activerecord 4.1.0.rc2 → 4.1.0

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

Potentially problematic release.


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

checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: ea5ed56a85b6c2570bb72ece981880267579ecf4
4
- data.tar.gz: d16aec37093f9ea61b393a28f1cc10952aef6003
3
+ metadata.gz: c715939fa3096f11569bb71814eb862c37e3d867
4
+ data.tar.gz: 715864fbf80ff9ea42f1f0ebaf440e70ed36d20d
5
5
  SHA512:
6
- metadata.gz: 5deb7e2666b956da509b5d8178cb28e4147ea7b3f34664df422553cc1d063f09777bb81ab5bceb3624cece5d4a88617f4e3e20394aae22db780fbae66b512071
7
- data.tar.gz: af8738dc598c8f482fde1bb4135eead1b955fd9d2b7632aaa17d7600b9b09a38e9df5be1e343616262838c03a00805a33a0f5111e4b51d9d330919c3424e3e56
6
+ metadata.gz: 2c9b80fd916e8bda4351846bb9aea10068df857f59c56a22c38c41f713eb2226e52a2f100696bd0927b7d40e109e2c5d5d87e8504efc6e3ac96198168029276e
7
+ data.tar.gz: b52925316b715e276d48d60aece84bb0e8de1e0cfcd17191c9cabeb76730f43fe73a5203b3e83fb5bbc3a14899451205809f1301c6bc924c43d7501d17f15193
@@ -1,3 +1,35 @@
1
+ * Fixed a problem where an enum would overwrite values of another enum
2
+ with the same name in an unrelated class.
3
+
4
+ Fixes #14607.
5
+
6
+ *Evan Whalen*
7
+
8
+ * Block a few default Class methods as scope name.
9
+
10
+ For instance, this will raise:
11
+
12
+ scope :public, -> { where(status: 1) }
13
+
14
+ *arthurnn*
15
+
16
+ * Deprecate SQLite database URLs containing an
17
+ authority.
18
+
19
+ The current "correct" spellings for in-memory, relative, and
20
+ absolute URLs, respectively, are:
21
+
22
+ sqlite3::memory:
23
+ sqlite3:relative/path
24
+ sqlite3:/full/path
25
+
26
+ The previous spelling (`sqlite3:///relative/path`) continues to work
27
+ as it did in Rails 4.0, but with a deprecation warning: in the next
28
+ release, that spelling will instead be interpreted as an absolute
29
+ path.
30
+
31
+ *Matthew Draper*
32
+
1
33
  * `where.not` adds `references` for `includes` like normal `where` calls do.
2
34
 
3
35
  Fixes #14406.
@@ -29,6 +29,8 @@ module ActiveRecord
29
29
  end
30
30
  }
31
31
 
32
+ BLACKLISTED_CLASS_METHODS = %w(private public protected)
33
+
32
34
  class AttributeMethodCache
33
35
  def initialize
34
36
  @module = Module.new
@@ -132,7 +134,7 @@ module ActiveRecord
132
134
  # A class method is 'dangerous' if it is already (re)defined by Active Record, but
133
135
  # not by any ancestors. (So 'puts' is not dangerous but 'new' is.)
134
136
  def dangerous_class_method?(method_name)
135
- class_method_defined_within?(method_name, Base)
137
+ BLACKLISTED_CLASS_METHODS.include?(method_name.to_s) || class_method_defined_within?(method_name, Base)
136
138
  end
137
139
 
138
140
  def class_method_defined_within?(name, klass, superklass = klass.superclass) # :nodoc
@@ -33,9 +33,15 @@ module ActiveRecord
33
33
  def initialize(url)
34
34
  raise "Database URL cannot be empty" if url.blank?
35
35
  @uri = URI.parse(url)
36
- @adapter = @uri.scheme
36
+ @adapter = @uri.scheme.gsub('-', '_')
37
37
  @adapter = "postgresql" if @adapter == "postgres"
38
- @query = @uri.query || ''
38
+
39
+ if @uri.opaque
40
+ @uri.opaque, @query = @uri.opaque.split('?', 2)
41
+ else
42
+ @query = @uri.query
43
+ end
44
+ @authority = url =~ %r{\A[^:]*://}
39
45
  end
40
46
 
41
47
  # Converts the given URL to a full connection hash.
@@ -65,30 +71,51 @@ module ActiveRecord
65
71
  # "localhost"
66
72
  # # => {}
67
73
  def query_hash
68
- Hash[@query.split("&").map { |pair| pair.split("=") }]
74
+ Hash[(@query || '').split("&").map { |pair| pair.split("=") }]
69
75
  end
70
76
 
71
77
  def raw_config
72
- query_hash.merge({
73
- "adapter" => @adapter,
74
- "username" => uri.user,
75
- "password" => uri.password,
76
- "port" => uri.port,
77
- "database" => database,
78
- "host" => uri.host })
78
+ if uri.opaque
79
+ query_hash.merge({
80
+ "adapter" => @adapter,
81
+ "database" => uri.opaque })
82
+ else
83
+ query_hash.merge({
84
+ "adapter" => @adapter,
85
+ "username" => uri.user,
86
+ "password" => uri.password,
87
+ "port" => uri.port,
88
+ "database" => database_from_path,
89
+ "host" => uri.host })
90
+ end
79
91
  end
80
92
 
81
93
  # Returns name of the database.
82
- # Sqlite3 expects this to be a full path or `:memory:`.
83
- def database
84
- if @adapter == 'sqlite3'
85
- if '/:memory:' == uri.path
86
- ':memory:'
87
- else
88
- uri.path
89
- end
94
+ # Sqlite3's handling of a leading slash is in transition as of
95
+ # Rails 4.1.
96
+ def database_from_path
97
+ if @authority && @adapter == 'sqlite3'
98
+ # 'sqlite3:///foo' is relative, for backwards compatibility.
99
+
100
+ database_name = uri.path.sub(%r{^/}, "")
101
+
102
+ msg = "Paths in SQLite3 database URLs of the form `sqlite3:///path` will be treated as absolute in Rails 4.2. " \
103
+ "Please switch to `sqlite3:#{database_name}`."
104
+ ActiveSupport::Deprecation.warn(msg)
105
+
106
+ database_name
107
+
108
+ elsif @adapter == 'sqlite3'
109
+ # 'sqlite3:/foo' is absolute, because that makes sense. The
110
+ # corresponding relative version, 'sqlite3:foo', is handled
111
+ # elsewhere, as an "opaque".
112
+
113
+ uri.path
90
114
  else
91
- uri.path.sub(%r{^/},"")
115
+ # Only SQLite uses a filename as the "database" name; for
116
+ # anything else, a leading slash would be silly.
117
+
118
+ uri.path.sub(%r{^/}, "")
92
119
  end
93
120
  end
94
121
  end
@@ -124,7 +151,7 @@ module ActiveRecord
124
151
  if config
125
152
  resolve_connection config
126
153
  elsif env = ActiveRecord::ConnectionHandling::RAILS_ENV.call
127
- resolve_env_connection env.to_sym
154
+ resolve_symbol_connection env.to_sym
128
155
  else
129
156
  raise AdapterNotSpecified
130
157
  end
@@ -193,42 +220,41 @@ module ActiveRecord
193
220
  #
194
221
  def resolve_connection(spec)
195
222
  case spec
196
- when Symbol, String
197
- resolve_env_connection spec
223
+ when Symbol
224
+ resolve_symbol_connection spec
225
+ when String
226
+ resolve_string_connection spec
198
227
  when Hash
199
228
  resolve_hash_connection spec
200
229
  end
201
230
  end
202
231
 
232
+ def resolve_string_connection(spec)
233
+ # Rails has historically accepted a string to mean either
234
+ # an environment key or a URL spec, so we have deprecated
235
+ # this ambiguous behaviour and in the future this function
236
+ # can be removed in favor of resolve_url_connection.
237
+ if configurations.key?(spec) || spec !~ /:/
238
+ ActiveSupport::Deprecation.warn "Passing a string to ActiveRecord::Base.establish_connection " \
239
+ "for a configuration lookup is deprecated, please pass a symbol (#{spec.to_sym.inspect}) instead"
240
+ resolve_symbol_connection(spec)
241
+ else
242
+ resolve_url_connection(spec)
243
+ end
244
+ end
245
+
203
246
  # Takes the environment such as `:production` or `:development`.
204
247
  # This requires that the @configurations was initialized with a key that
205
248
  # matches.
206
249
  #
207
- #
208
- # Resolver.new("production" => {}).resolve_env_connection(:production)
250
+ # Resolver.new("production" => {}).resolve_symbol_connection(:production)
209
251
  # # => {}
210
252
  #
211
- # Takes a connection URL.
212
- #
213
- # Resolver.new({}).resolve_env_connection("postgresql://localhost/foo")
214
- # # => { "host" => "localhost", "database" => "foo", "adapter" => "postgresql" }
215
- #
216
- def resolve_env_connection(spec)
217
- # Rails has historically accepted a string to mean either
218
- # an environment key or a URL spec, so we have deprecated
219
- # this ambiguous behaviour and in the future this function
220
- # can be removed in favor of resolve_string_connection and
221
- # resolve_symbol_connection.
253
+ def resolve_symbol_connection(spec)
222
254
  if config = configurations[spec.to_s]
223
- if spec.is_a?(String)
224
- ActiveSupport::Deprecation.warn "Passing a string to ActiveRecord::Base.establish_connection " \
225
- "for a configuration lookup is deprecated, please pass a symbol (#{spec.to_sym.inspect}) instead"
226
- end
227
255
  resolve_connection(config)
228
- elsif spec.is_a?(String)
229
- resolve_string_connection(spec)
230
256
  else
231
- raise(AdapterNotSpecified, "'#{spec}' database is not configured. Available configuration: #{configurations.inspect}")
257
+ raise(AdapterNotSpecified, "'#{spec}' database is not configured. Available: #{configurations.keys.inspect}")
232
258
  end
233
259
  end
234
260
 
@@ -244,7 +270,12 @@ module ActiveRecord
244
270
  spec
245
271
  end
246
272
 
247
- def resolve_string_connection(url)
273
+ # Takes a connection URL.
274
+ #
275
+ # Resolver.new({}).resolve_url_connection("postgresql://localhost/foo")
276
+ # # => { "host" => "localhost", "database" => "foo", "adapter" => "postgresql" }
277
+ #
278
+ def resolve_url_connection(url)
248
279
  ConnectionUrlResolver.new(url).to_hash
249
280
  end
250
281
  end
@@ -58,9 +58,9 @@ module ActiveRecord
58
58
  end
59
59
 
60
60
  class MergeAndResolveDefaultUrlConfig # :nodoc:
61
- def initialize(raw_configurations, url = ENV['DATABASE_URL'])
61
+ def initialize(raw_configurations)
62
62
  @raw_config = raw_configurations.dup
63
- @url = url
63
+ @env = DEFAULT_ENV.call.to_s
64
64
  end
65
65
 
66
66
  # Returns fully resolved connection hashes.
@@ -71,33 +71,10 @@ module ActiveRecord
71
71
 
72
72
  private
73
73
  def config
74
- if @url
75
- raw_merged_into_default
76
- else
77
- @raw_config
78
- end
79
- end
80
-
81
- def raw_merged_into_default
82
- default = default_url_hash
83
-
84
- @raw_config.each do |env, values|
85
- default[env] = values || {}
86
- default[env].merge!("url" => @url) { |h, v1, v2| v1 || v2 } if default[env].is_a?(Hash)
87
- end
88
- default
89
- end
90
-
91
- # When the raw configuration is not present and ENV['DATABASE_URL']
92
- # is available we return a hash with the connection information in
93
- # the connection URL. This hash responds to any string key with
94
- # resolved connection information.
95
- def default_url_hash
96
- Hash.new do |hash, key|
97
- hash[key] = if key.is_a? String
98
- ActiveRecord::ConnectionAdapters::ConnectionSpecification::ConnectionUrlResolver.new(@url).to_hash
99
- else
100
- nil
74
+ @raw_config.dup.tap do |cfg|
75
+ if url = ENV['DATABASE_URL']
76
+ cfg[@env] ||= {}
77
+ cfg[@env]["url"] ||= url
101
78
  end
102
79
  end
103
80
  end
@@ -299,7 +299,7 @@ module ActiveRecord
299
299
  def ==(comparison_object)
300
300
  super ||
301
301
  comparison_object.instance_of?(self.class) &&
302
- id &&
302
+ !id.nil? &&
303
303
  comparison_object.id == id
304
304
  end
305
305
  alias :eql? :==
@@ -1,3 +1,5 @@
1
+ require 'active_support/core_ext/object/deep_dup'
2
+
1
3
  module ActiveRecord
2
4
  # Declare an enum attribute where the values map to integers in the database,
3
5
  # but can be queried by name. Example:
@@ -65,10 +67,14 @@ module ActiveRecord
65
67
  #
66
68
  # Where conditions on an enum attribute must use the ordinal value of an enum.
67
69
  module Enum
68
- DEFINED_ENUMS = {} # :nodoc:
70
+ def self.extended(base)
71
+ base.class_attribute(:defined_enums)
72
+ base.defined_enums = {}
73
+ end
69
74
 
70
- def enum_mapping_for(attr_name) # :nodoc:
71
- DEFINED_ENUMS[attr_name.to_s]
75
+ def inherited(base)
76
+ base.defined_enums = defined_enums.deep_dup
77
+ super
72
78
  end
73
79
 
74
80
  def enum(definitions)
@@ -122,9 +128,8 @@ module ActiveRecord
122
128
  klass.send(:detect_enum_conflict!, name, value, true)
123
129
  klass.scope value, -> { klass.where name => i }
124
130
  end
125
-
126
- DEFINED_ENUMS[name.to_s] = enum_values
127
131
  end
132
+ defined_enums[name.to_s] = enum_values
128
133
  end
129
134
  end
130
135
 
@@ -134,7 +139,7 @@ module ActiveRecord
134
139
  mod = Module.new do
135
140
  private
136
141
  def save_changed_attribute(attr_name, value)
137
- if (mapping = self.class.enum_mapping_for(attr_name))
142
+ if (mapping = self.class.defined_enums[attr_name.to_s])
138
143
  if attribute_changed?(attr_name)
139
144
  old = changed_attributes[attr_name]
140
145
 
@@ -8,7 +8,7 @@ module ActiveRecord
8
8
  MAJOR = 4
9
9
  MINOR = 1
10
10
  TINY = 0
11
- PRE = "rc2"
11
+ PRE = nil
12
12
 
13
13
  STRING = [MAJOR, MINOR, TINY, PRE].compact.join(".")
14
14
  end
@@ -151,7 +151,7 @@ module ActiveRecord
151
151
  super ||
152
152
  other_aggregation.kind_of?(self.class) &&
153
153
  name == other_aggregation.name &&
154
- other_aggregation.options &&
154
+ !other_aggregation.options.nil? &&
155
155
  active_record == other_aggregation.active_record
156
156
  end
157
157
 
@@ -231,7 +231,7 @@ module ActiveRecord
231
231
 
232
232
  def execute_simple_calculation(operation, column_name, distinct) #:nodoc:
233
233
  # Postgresql doesn't like ORDER BY when there are no GROUP BY
234
- relation = reorder(nil)
234
+ relation = unscope(:order)
235
235
 
236
236
  column_alias = column_name
237
237
 
@@ -93,8 +93,8 @@ module ActiveRecord
93
93
  value
94
94
  end
95
95
 
96
- def map_enum_attribute(klass,attribute,value)
97
- mapping = klass.enum_mapping_for(attribute.to_s)
96
+ def map_enum_attribute(klass, attribute, value)
97
+ mapping = klass.defined_enums[attribute.to_s]
98
98
  value = mapping[value] if value && mapping
99
99
  value
100
100
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: activerecord
3
3
  version: !ruby/object:Gem::Version
4
- version: 4.1.0.rc2
4
+ version: 4.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - David Heinemeier Hansson
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-03-25 00:00:00.000000000 Z
11
+ date: 2014-04-08 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activesupport
@@ -16,28 +16,28 @@ dependencies:
16
16
  requirements:
17
17
  - - '='
18
18
  - !ruby/object:Gem::Version
19
- version: 4.1.0.rc2
19
+ version: 4.1.0
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - '='
25
25
  - !ruby/object:Gem::Version
26
- version: 4.1.0.rc2
26
+ version: 4.1.0
27
27
  - !ruby/object:Gem::Dependency
28
28
  name: activemodel
29
29
  requirement: !ruby/object:Gem::Requirement
30
30
  requirements:
31
31
  - - '='
32
32
  - !ruby/object:Gem::Version
33
- version: 4.1.0.rc2
33
+ version: 4.1.0
34
34
  type: :runtime
35
35
  prerelease: false
36
36
  version_requirements: !ruby/object:Gem::Requirement
37
37
  requirements:
38
38
  - - '='
39
39
  - !ruby/object:Gem::Version
40
- version: 4.1.0.rc2
40
+ version: 4.1.0
41
41
  - !ruby/object:Gem::Dependency
42
42
  name: arel
43
43
  requirement: !ruby/object:Gem::Requirement
@@ -242,9 +242,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
242
242
  version: 1.9.3
243
243
  required_rubygems_version: !ruby/object:Gem::Requirement
244
244
  requirements:
245
- - - ">"
245
+ - - ">="
246
246
  - !ruby/object:Gem::Version
247
- version: 1.3.1
247
+ version: '0'
248
248
  requirements: []
249
249
  rubyforge_project:
250
250
  rubygems_version: 2.2.0