activesupport 3.0.0.beta → 3.0.0.beta2
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.
- data/CHANGELOG +15 -1
- data/lib/active_support.rb +3 -0
- data/lib/active_support/all.rb +0 -1
- data/lib/active_support/cache/mem_cache_store.rb +1 -1
- data/lib/active_support/callbacks.rb +2 -2
- data/lib/active_support/core_ext/array/conversions.rb +0 -1
- data/lib/active_support/core_ext/array/extract_options.rb +16 -1
- data/lib/active_support/core_ext/class.rb +1 -0
- data/lib/active_support/core_ext/class/attribute.rb +30 -5
- data/lib/active_support/core_ext/class/attribute_accessors.rb +33 -27
- data/lib/active_support/core_ext/class/delegating_attributes.rb +10 -7
- data/lib/active_support/core_ext/class/subclasses.rb +55 -0
- data/lib/active_support/core_ext/date_time/conversions.rb +1 -0
- data/lib/active_support/core_ext/file/atomic.rb +3 -2
- data/lib/active_support/core_ext/file/path.rb +5 -0
- data/lib/active_support/core_ext/hash/conversions.rb +9 -0
- data/lib/active_support/core_ext/kernel.rb +0 -1
- data/lib/active_support/core_ext/kernel/debugger.rb +1 -1
- data/lib/active_support/core_ext/kernel/reporting.rb +1 -1
- data/lib/active_support/core_ext/module.rb +5 -3
- data/lib/active_support/core_ext/module/anonymous.rb +24 -0
- data/lib/active_support/core_ext/module/attribute_accessors.rb +25 -21
- data/lib/active_support/core_ext/module/delegation.rb +20 -9
- data/lib/active_support/core_ext/module/introspection.rb +8 -8
- data/lib/active_support/core_ext/module/method_names.rb +14 -0
- data/lib/active_support/core_ext/module/reachable.rb +10 -0
- data/lib/active_support/core_ext/module/remove_method.rb +6 -0
- data/lib/active_support/core_ext/object.rb +7 -1
- data/lib/active_support/core_ext/object/extending.rb +11 -0
- data/lib/active_support/core_ext/object/singleton_class.rb +13 -0
- data/lib/active_support/core_ext/proc.rb +3 -3
- data/lib/active_support/core_ext/string/conversions.rb +1 -0
- data/lib/active_support/core_ext/string/inflections.rb +1 -1
- data/lib/active_support/core_ext/string/interpolation.rb +1 -91
- data/lib/active_support/core_ext/string/output_safety.rb +12 -8
- data/lib/active_support/core_ext/string/xchar.rb +1 -1
- data/lib/active_support/core_ext/time/conversions.rb +1 -0
- data/lib/active_support/core_ext/time/marshal.rb +56 -0
- data/lib/active_support/dependencies.rb +146 -191
- data/lib/active_support/dependencies/autoload.rb +1 -0
- data/lib/active_support/deprecation/method_wrappers.rb +9 -9
- data/lib/active_support/deprecation/reporting.rb +2 -1
- data/lib/active_support/hash_with_indifferent_access.rb +4 -0
- data/lib/active_support/i18n.rb +2 -1
- data/lib/active_support/inflector/methods.rb +1 -1
- data/lib/active_support/inflector/transliterate.rb +3 -3
- data/lib/active_support/json/backends/yajl.rb +40 -0
- data/lib/active_support/json/decoding.rb +16 -1
- data/lib/active_support/lazy_load_hooks.rb +17 -0
- data/lib/active_support/memoizable.rb +1 -1
- data/lib/active_support/multibyte.rb +2 -2
- data/lib/active_support/multibyte/utils.rb +1 -1
- data/lib/active_support/notifications.rb +7 -3
- data/lib/active_support/notifications/fanout.rb +19 -5
- data/lib/active_support/ordered_options.rb +6 -0
- data/lib/active_support/railtie.rb +9 -9
- data/lib/active_support/ruby/shim.rb +2 -0
- data/lib/active_support/test_case.rb +2 -7
- data/lib/active_support/testing/assertions.rb +15 -0
- data/lib/active_support/testing/isolation.rb +2 -2
- data/lib/active_support/time.rb +1 -1
- data/lib/active_support/values/time_zone.rb +7 -4
- data/lib/active_support/version.rb +3 -2
- data/lib/active_support/whiny_nil.rb +4 -5
- data/lib/active_support/xml_mini/libxmlsax.rb +1 -0
- data/lib/active_support/xml_mini/nokogirisax.rb +1 -0
- data/lib/active_support/xml_mini/rexml.rb +7 -1
- metadata +65 -31
- data/lib/active_support/core_ext/kernel/daemonizing.rb +0 -7
- data/lib/active_support/core_ext/module/inclusion.rb +0 -30
- data/lib/active_support/core_ext/module/loading.rb +0 -25
- data/lib/active_support/core_ext/object/metaclass.rb +0 -13
- data/lib/active_support/core_ext/time/marshal_with_utc_flag.rb +0 -22
@@ -12,15 +12,15 @@ module ActiveSupport
|
|
12
12
|
method_names.each do |method_name|
|
13
13
|
target_module.alias_method_chain(method_name, :deprecation) do |target, punctuation|
|
14
14
|
target_module.module_eval(<<-end_eval, __FILE__, __LINE__ + 1)
|
15
|
-
def #{target}_with_deprecation#{punctuation}(*args, &block)
|
16
|
-
::ActiveSupport::Deprecation.warn(
|
17
|
-
::ActiveSupport::Deprecation.deprecated_method_warning(
|
18
|
-
:#{method_name},
|
19
|
-
#{options[method_name].inspect}),
|
20
|
-
caller
|
21
|
-
)
|
22
|
-
send(:#{target}_without_deprecation#{punctuation}, *args, &block)
|
23
|
-
end
|
15
|
+
def #{target}_with_deprecation#{punctuation}(*args, &block)
|
16
|
+
::ActiveSupport::Deprecation.warn(
|
17
|
+
::ActiveSupport::Deprecation.deprecated_method_warning(
|
18
|
+
:#{method_name},
|
19
|
+
#{options[method_name].inspect}),
|
20
|
+
caller
|
21
|
+
)
|
22
|
+
send(:#{target}_without_deprecation#{punctuation}, *args, &block)
|
23
|
+
end
|
24
24
|
end_eval
|
25
25
|
end
|
26
26
|
end
|
@@ -29,7 +29,8 @@ module ActiveSupport
|
|
29
29
|
private
|
30
30
|
def deprecation_message(callstack, message = nil)
|
31
31
|
message ||= "You are using deprecated behavior which will be removed from the next major or minor release."
|
32
|
-
|
32
|
+
message += '.' unless message =~ /\.$/
|
33
|
+
"DEPRECATION WARNING: #{message} #{deprecation_caller_message(callstack)}"
|
33
34
|
end
|
34
35
|
|
35
36
|
def deprecation_caller_message(callstack)
|
data/lib/active_support/i18n.rb
CHANGED
@@ -109,7 +109,7 @@ module ActiveSupport
|
|
109
109
|
|
110
110
|
constant = Object
|
111
111
|
names.each do |name|
|
112
|
-
constant = constant.
|
112
|
+
constant = constant.const_defined?(name, false) ? constant.const_get(name) : constant.const_missing(name)
|
113
113
|
end
|
114
114
|
constant
|
115
115
|
end
|
@@ -14,8 +14,8 @@ module ActiveSupport
|
|
14
14
|
if RUBY_VERSION >= '1.9'
|
15
15
|
undef_method :transliterate
|
16
16
|
def transliterate(string)
|
17
|
-
|
18
|
-
|
17
|
+
proxy = ActiveSupport::Multibyte.proxy_class.new(string)
|
18
|
+
proxy.normalize(:kd).gsub(/[^\x00-\x7F]+/, '')
|
19
19
|
end
|
20
20
|
|
21
21
|
# The iconv transliteration code doesn't function correctly
|
@@ -47,7 +47,7 @@ module ActiveSupport
|
|
47
47
|
# replace accented chars with their ascii equivalents
|
48
48
|
parameterized_string = transliterate(string)
|
49
49
|
# Turn unwanted chars into the separator
|
50
|
-
parameterized_string.gsub!(/[^a-z0-9\-_
|
50
|
+
parameterized_string.gsub!(/[^a-z0-9\-_]+/i, sep)
|
51
51
|
unless sep.nil? || sep.empty?
|
52
52
|
re_sep = Regexp.escape(sep)
|
53
53
|
# No more than one of the separator in a row.
|
@@ -0,0 +1,40 @@
|
|
1
|
+
require 'yajl-ruby' unless defined?(Yajl)
|
2
|
+
|
3
|
+
module ActiveSupport
|
4
|
+
module JSON
|
5
|
+
module Backends
|
6
|
+
module Yajl
|
7
|
+
ParseError = ::Yajl::ParseError
|
8
|
+
extend self
|
9
|
+
|
10
|
+
# Parses a JSON string or IO and convert it into an object
|
11
|
+
def decode(json)
|
12
|
+
data = ::Yajl::Parser.new.parse(json)
|
13
|
+
if ActiveSupport.parse_json_times
|
14
|
+
convert_dates_from(data)
|
15
|
+
else
|
16
|
+
data
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
private
|
21
|
+
def convert_dates_from(data)
|
22
|
+
case data
|
23
|
+
when nil
|
24
|
+
nil
|
25
|
+
when DATE_REGEX
|
26
|
+
DateTime.parse(data)
|
27
|
+
when Array
|
28
|
+
data.map! { |d| convert_dates_from(d) }
|
29
|
+
when Hash
|
30
|
+
data.each do |key, value|
|
31
|
+
data[key] = convert_dates_from(value)
|
32
|
+
end
|
33
|
+
else
|
34
|
+
data
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
@@ -6,12 +6,15 @@ module ActiveSupport
|
|
6
6
|
mattr_accessor :parse_json_times
|
7
7
|
|
8
8
|
module JSON
|
9
|
+
# Listed in order of preference.
|
10
|
+
DECODERS = %w(Yajl Yaml)
|
11
|
+
|
9
12
|
class << self
|
10
13
|
attr_reader :parse_error
|
11
14
|
delegate :decode, :to => :backend
|
12
15
|
|
13
16
|
def backend
|
14
|
-
|
17
|
+
set_default_backend unless defined?(@backend)
|
15
18
|
@backend
|
16
19
|
end
|
17
20
|
|
@@ -31,6 +34,18 @@ module ActiveSupport
|
|
31
34
|
ensure
|
32
35
|
self.backend = old_backend
|
33
36
|
end
|
37
|
+
|
38
|
+
def set_default_backend
|
39
|
+
DECODERS.find do |name|
|
40
|
+
begin
|
41
|
+
self.backend = name
|
42
|
+
true
|
43
|
+
rescue LoadError
|
44
|
+
# Try next decoder.
|
45
|
+
false
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
34
49
|
end
|
35
50
|
end
|
36
51
|
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
module ActiveSupport
|
2
|
+
@load_hooks = Hash.new {|h,k| h[k] = [] }
|
3
|
+
@loaded = {}
|
4
|
+
|
5
|
+
def self.on_load(name, &block)
|
6
|
+
if base = @loaded[name]
|
7
|
+
base.instance_eval(&block)
|
8
|
+
else
|
9
|
+
@load_hooks[name] << block
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
def self.run_load_hooks(name, base = Object)
|
14
|
+
@load_hooks[name].each { |hook| base.instance_eval(&hook) }
|
15
|
+
@loaded[name] = base
|
16
|
+
end
|
17
|
+
end
|
@@ -53,8 +53,8 @@ module ActiveSupport #:nodoc:
|
|
53
53
|
\xf4 [\x80-\x8f] [\x80-\xbf] [\x80-\xbf])\z /xn,
|
54
54
|
# Quick check for valid Shift-JIS characters, disregards the odd-even pairing
|
55
55
|
'Shift_JIS' => /\A(?:
|
56
|
-
[\x00-\x7e
|
57
|
-
[\x81-\x9f
|
56
|
+
[\x00-\x7e\xa1-\xdf] |
|
57
|
+
[\x81-\x9f\xe0-\xef] [\x40-\x7e\x80-\x9e\x9f-\xfc])\z /xn
|
58
58
|
}
|
59
59
|
end
|
60
60
|
end
|
@@ -27,7 +27,7 @@ module ActiveSupport #:nodoc:
|
|
27
27
|
def self.verify(string)
|
28
28
|
if expression = valid_character
|
29
29
|
# Splits the string on character boundaries, which are determined based on $KCODE.
|
30
|
-
string.split(//).all? { |c| expression
|
30
|
+
string.split(//).all? { |c| expression =~ c }
|
31
31
|
else
|
32
32
|
true
|
33
33
|
end
|
@@ -9,7 +9,7 @@ module ActiveSupport
|
|
9
9
|
# end
|
10
10
|
#
|
11
11
|
# You can consume those events and the information they provide by registering
|
12
|
-
# a subscriber. For instance, let's store all instrumented events in an array:
|
12
|
+
# a log subscriber. For instance, let's store all instrumented events in an array:
|
13
13
|
#
|
14
14
|
# @events = []
|
15
15
|
#
|
@@ -35,7 +35,7 @@ module ActiveSupport
|
|
35
35
|
# end
|
36
36
|
#
|
37
37
|
# Notifications ships with a queue implementation that consumes and publish events
|
38
|
-
# to subscribers in a thread. You can use any queue implementation you want.
|
38
|
+
# to log subscribers in a thread. You can use any queue implementation you want.
|
39
39
|
#
|
40
40
|
module Notifications
|
41
41
|
autoload :Instrumenter, 'active_support/notifications/instrumenter'
|
@@ -44,7 +44,7 @@ module ActiveSupport
|
|
44
44
|
|
45
45
|
class << self
|
46
46
|
attr_writer :notifier
|
47
|
-
delegate :publish, :subscribe, :to => :notifier
|
47
|
+
delegate :publish, :subscribe, :unsubscribe, :to => :notifier
|
48
48
|
delegate :instrument, :to => :instrumenter
|
49
49
|
|
50
50
|
def notifier
|
@@ -69,6 +69,10 @@ module ActiveSupport
|
|
69
69
|
@queue.bind(pattern).subscribe(&block)
|
70
70
|
end
|
71
71
|
|
72
|
+
def unsubscribe(subscriber)
|
73
|
+
@queue.unsubscribe(subscriber)
|
74
|
+
end
|
75
|
+
|
72
76
|
def wait
|
73
77
|
@queue.wait
|
74
78
|
end
|
@@ -1,10 +1,11 @@
|
|
1
1
|
module ActiveSupport
|
2
2
|
module Notifications
|
3
3
|
# This is a default queue implementation that ships with Notifications. It
|
4
|
-
# just pushes events to all registered subscribers.
|
4
|
+
# just pushes events to all registered log subscribers.
|
5
5
|
class Fanout
|
6
6
|
def initialize
|
7
7
|
@subscribers = []
|
8
|
+
@listeners_for = {}
|
8
9
|
end
|
9
10
|
|
10
11
|
def bind(pattern)
|
@@ -12,11 +13,22 @@ module ActiveSupport
|
|
12
13
|
end
|
13
14
|
|
14
15
|
def subscribe(pattern = nil, &block)
|
16
|
+
@listeners_for.clear
|
15
17
|
@subscribers << Subscriber.new(pattern, &block)
|
18
|
+
@subscribers.last
|
16
19
|
end
|
17
20
|
|
18
|
-
def
|
19
|
-
@subscribers.
|
21
|
+
def unsubscribe(subscriber)
|
22
|
+
@subscribers.delete(subscriber)
|
23
|
+
@listeners_for.clear
|
24
|
+
end
|
25
|
+
|
26
|
+
def publish(name, *args)
|
27
|
+
if listeners = @listeners_for[name]
|
28
|
+
listeners.each { |s| s.publish(name, *args) }
|
29
|
+
else
|
30
|
+
@listeners_for[name] = @subscribers.select { |s| s.publish(name, *args) }
|
31
|
+
end
|
20
32
|
end
|
21
33
|
|
22
34
|
# This is a sync queue, so there is not waiting.
|
@@ -32,7 +44,7 @@ module ActiveSupport
|
|
32
44
|
when Regexp, NilClass
|
33
45
|
pattern
|
34
46
|
else
|
35
|
-
/^#{Regexp.escape(pattern.to_s)}
|
47
|
+
/^#{Regexp.escape(pattern.to_s)}$/
|
36
48
|
end
|
37
49
|
end
|
38
50
|
|
@@ -48,7 +60,9 @@ module ActiveSupport
|
|
48
60
|
end
|
49
61
|
|
50
62
|
def publish(*args)
|
51
|
-
|
63
|
+
return unless matches?(args.first)
|
64
|
+
push(*args)
|
65
|
+
true
|
52
66
|
end
|
53
67
|
|
54
68
|
def drained?
|
@@ -3,7 +3,7 @@ require "rails"
|
|
3
3
|
|
4
4
|
module ActiveSupport
|
5
5
|
class Railtie < Rails::Railtie
|
6
|
-
|
6
|
+
config.active_support = ActiveSupport::OrderedOptions.new
|
7
7
|
|
8
8
|
# Loads support for "whiny nil" (noisy warnings when methods are invoked
|
9
9
|
# on +nil+ values) if Configuration#whiny_nils is true.
|
@@ -30,17 +30,17 @@ end
|
|
30
30
|
|
31
31
|
module I18n
|
32
32
|
class Railtie < Rails::Railtie
|
33
|
-
|
34
|
-
|
35
|
-
# Initialize I18n load paths to an array
|
36
|
-
config.i18n.engines_load_path = []
|
33
|
+
config.i18n = ActiveSupport::OrderedOptions.new
|
34
|
+
config.i18n.railties_load_path = []
|
37
35
|
config.i18n.load_path = []
|
38
36
|
|
39
37
|
initializer "i18n.initialize" do
|
40
|
-
|
41
|
-
|
42
|
-
ActionDispatch::Callbacks.to_prepare do
|
38
|
+
ActiveSupport.on_load(:i18n) do
|
43
39
|
I18n.reload!
|
40
|
+
|
41
|
+
ActionDispatch::Callbacks.to_prepare do
|
42
|
+
I18n.reload!
|
43
|
+
end
|
44
44
|
end
|
45
45
|
end
|
46
46
|
|
@@ -49,7 +49,7 @@ module I18n
|
|
49
49
|
config.after_initialize do |app|
|
50
50
|
app.config.i18n.each do |setting, value|
|
51
51
|
case setting
|
52
|
-
when :
|
52
|
+
when :railties_load_path
|
53
53
|
app.config.i18n.load_path.unshift(*value)
|
54
54
|
when :load_path
|
55
55
|
I18n.load_path += value
|
@@ -17,3 +17,5 @@ require 'active_support/core_ext/string/conversions'
|
|
17
17
|
require 'active_support/core_ext/string/interpolation'
|
18
18
|
require 'active_support/core_ext/rexml'
|
19
19
|
require 'active_support/core_ext/time/conversions'
|
20
|
+
require 'active_support/core_ext/file/path'
|
21
|
+
require 'active_support/core_ext/module/method_names'
|
@@ -5,9 +5,10 @@ require 'active_support/testing/deprecation'
|
|
5
5
|
require 'active_support/testing/declarative'
|
6
6
|
require 'active_support/testing/pending'
|
7
7
|
require 'active_support/testing/isolation'
|
8
|
+
require 'active_support/core_ext/kernel/reporting'
|
8
9
|
|
9
10
|
begin
|
10
|
-
require 'mocha'
|
11
|
+
silence_warnings { require 'mocha' }
|
11
12
|
rescue LoadError
|
12
13
|
# Fake Mocha::ExpectationError so we can rescue it in #run. Bleh.
|
13
14
|
Object.const_set :Mocha, Module.new
|
@@ -21,12 +22,6 @@ module ActiveSupport
|
|
21
22
|
alias_method :method_name, :name if method_defined? :name
|
22
23
|
alias_method :method_name, :__name__ if method_defined? :__name__
|
23
24
|
else
|
24
|
-
# TODO: Figure out how to get the Rails::BacktraceFilter into minitest/unit
|
25
|
-
if defined?(Rails) && ENV['BACKTRACE'].nil?
|
26
|
-
require 'rails/backtrace_cleaner'
|
27
|
-
Test::Unit::Util::BacktraceFilter.module_eval { include Rails::BacktraceFilterForTestUnit }
|
28
|
-
end
|
29
|
-
|
30
25
|
Assertion = Test::Unit::AssertionFailedError
|
31
26
|
|
32
27
|
require 'active_support/testing/default'
|
@@ -1,4 +1,5 @@
|
|
1
1
|
require 'active_support/core_ext/array/wrap'
|
2
|
+
require 'active_support/core_ext/object/blank'
|
2
3
|
|
3
4
|
module ActiveSupport
|
4
5
|
module Testing
|
@@ -62,6 +63,20 @@ module ActiveSupport
|
|
62
63
|
def assert_no_difference(expression, message = nil, &block)
|
63
64
|
assert_difference expression, 0, message, &block
|
64
65
|
end
|
66
|
+
|
67
|
+
# Test if an expression is blank. Passes if object.blank? is true.
|
68
|
+
#
|
69
|
+
# assert_blank [] # => true
|
70
|
+
def assert_blank(object)
|
71
|
+
assert object.blank?, "#{object.inspect} is not blank"
|
72
|
+
end
|
73
|
+
|
74
|
+
# Test if an expression is not blank. Passes if object.present? is true.
|
75
|
+
#
|
76
|
+
# assert_present {:data => 'x' } # => true
|
77
|
+
def assert_present(object)
|
78
|
+
assert object.present?, "#{object.inspect} is blank"
|
79
|
+
end
|
65
80
|
end
|
66
81
|
end
|
67
82
|
end
|
data/lib/active_support/time.rb
CHANGED
@@ -14,7 +14,7 @@ require 'date'
|
|
14
14
|
require 'time'
|
15
15
|
|
16
16
|
require 'active_support/core_ext/time/publicize_conversion_methods'
|
17
|
-
require 'active_support/core_ext/time/
|
17
|
+
require 'active_support/core_ext/time/marshal'
|
18
18
|
require 'active_support/core_ext/time/acts_like'
|
19
19
|
require 'active_support/core_ext/time/calculations'
|
20
20
|
require 'active_support/core_ext/time/conversions'
|