activerecord 3.2.12 → 3.2.13.rc1
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 +4 -4
- data/CHANGELOG.md +309 -2
- data/lib/active_record/associations/association.rb +2 -1
- data/lib/active_record/associations/has_many_through_association.rb +5 -14
- data/lib/active_record/associations/has_one_association.rb +9 -1
- data/lib/active_record/associations/preloader/through_association.rb +2 -1
- data/lib/active_record/attribute_methods/serialization.rb +18 -0
- data/lib/active_record/attribute_methods/time_zone_conversion.rb +6 -14
- data/lib/active_record/attribute_methods/write.rb +5 -4
- data/lib/active_record/base.rb +3 -3
- data/lib/active_record/connection_adapters/abstract/database_statements.rb +1 -1
- data/lib/active_record/connection_adapters/abstract/quoting.rb +2 -8
- data/lib/active_record/connection_adapters/abstract_mysql_adapter.rb +2 -0
- data/lib/active_record/connection_adapters/column.rb +1 -1
- data/lib/active_record/connection_adapters/mysql_adapter.rb +1 -1
- data/lib/active_record/connection_adapters/postgresql_adapter.rb +16 -8
- data/lib/active_record/connection_adapters/schema_cache.rb +20 -1
- data/lib/active_record/connection_adapters/sqlite_adapter.rb +7 -3
- data/lib/active_record/explain.rb +7 -6
- data/lib/active_record/integration.rb +12 -1
- data/lib/active_record/locking/optimistic.rb +2 -0
- data/lib/active_record/log_subscriber.rb +5 -1
- data/lib/active_record/migration.rb +2 -2
- data/lib/active_record/nested_attributes.rb +4 -3
- data/lib/active_record/persistence.rb +1 -1
- data/lib/active_record/query_cache.rb +6 -6
- data/lib/active_record/railtie.rb +7 -0
- data/lib/active_record/railties/databases.rake +22 -8
- data/lib/active_record/relation/batches.rb +2 -2
- data/lib/active_record/relation/calculations.rb +11 -3
- data/lib/active_record/relation/finder_methods.rb +5 -3
- data/lib/active_record/relation/predicate_builder.rb +0 -4
- data/lib/active_record/scoping/named.rb +1 -3
- data/lib/active_record/validations/uniqueness.rb +1 -1
- data/lib/active_record/version.rb +2 -2
- metadata +15 -15
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: d152752397963fbb89a3df0673c3fc204a8ad09d
|
4
|
+
data.tar.gz: 68758aa69846d6dee43c968e7ec8256db958a44b
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 9cf4972e5c7a8b5f1880650b0e3f9716c0606773863ca640cea5a71677f1fa6db9095534f25e445644740a98a5ae410a787832c925f19555196cfe7188cab88d
|
7
|
+
data.tar.gz: 5f334b07081d7c3bf46b1af59e2123f9e38b2820b89b3b488b549ab98eca8bd656295fdf09f1eb6e01ede7b18c0e8ca67a1beb5b110c57344e2b4bfb161f903d
|
data/CHANGELOG.md
CHANGED
@@ -1,4 +1,304 @@
|
|
1
|
-
##
|
1
|
+
## unreleased ##
|
2
|
+
|
3
|
+
* No changes.
|
4
|
+
|
5
|
+
|
6
|
+
## Rails 3.2.13 (Feb 17, 2013) ##
|
7
|
+
|
8
|
+
* Reverted 921a296a3390192a71abeec6d9a035cc6d1865c8, 'Quote numeric values
|
9
|
+
compared to string columns.' This caused several regressions.
|
10
|
+
|
11
|
+
*Steve Klabnik*
|
12
|
+
|
13
|
+
* Fix overriding of attributes by default_scope on `ActiveRecord::Base#dup`.
|
14
|
+
|
15
|
+
*Hiroshige UMINO*
|
16
|
+
|
17
|
+
* Fix issue with overriding Active Record reader methods with a composed object
|
18
|
+
and using that attribute as the scope of a `uniqueness_of` validation.
|
19
|
+
Backport #7072.
|
20
|
+
|
21
|
+
*Peter Brown*
|
22
|
+
|
23
|
+
* Sqlite now preserves custom primary keys when copying or altering tables.
|
24
|
+
Fixes #9367.
|
25
|
+
Backport #2312.
|
26
|
+
|
27
|
+
*Sean Scally + Yves Senn*
|
28
|
+
|
29
|
+
* Preloading `has_many :through` associations with conditions won't
|
30
|
+
cache the `:through` association. This will prevent invalid
|
31
|
+
subsets to be cached.
|
32
|
+
Fixes #8423.
|
33
|
+
Backport #9252.
|
34
|
+
|
35
|
+
Example:
|
36
|
+
|
37
|
+
class User
|
38
|
+
has_many :posts
|
39
|
+
has_many :recent_comments, -> { where('created_at > ?', 1.week.ago) }, :through => :posts
|
40
|
+
end
|
41
|
+
|
42
|
+
a_user = User.includes(:recent_comments).first
|
43
|
+
|
44
|
+
# this is preloaded
|
45
|
+
a_user.recent_comments
|
46
|
+
|
47
|
+
# fetching the recent_comments through the posts association won't preload it.
|
48
|
+
a_user.posts
|
49
|
+
|
50
|
+
*Yves Senn*
|
51
|
+
|
52
|
+
* Fix handling of dirty time zone aware attributes
|
53
|
+
|
54
|
+
Previously, when `time_zone_aware_attributes` were enabled, after
|
55
|
+
changing a datetime or timestamp attribute and then changing it back
|
56
|
+
to the original value, `changed_attributes` still tracked the
|
57
|
+
attribute as changed. This caused `[attribute]_changed?` and
|
58
|
+
`changed?` methods to return true incorrectly.
|
59
|
+
|
60
|
+
Example:
|
61
|
+
|
62
|
+
in_time_zone 'Paris' do
|
63
|
+
order = Order.new
|
64
|
+
original_time = Time.local(2012, 10, 10)
|
65
|
+
order.shipped_at = original_time
|
66
|
+
order.save
|
67
|
+
order.changed? # => false
|
68
|
+
|
69
|
+
# changing value
|
70
|
+
order.shipped_at = Time.local(2013, 1, 1)
|
71
|
+
order.changed? # => true
|
72
|
+
|
73
|
+
# reverting to original value
|
74
|
+
order.shipped_at = original_time
|
75
|
+
order.changed? # => false, used to return true
|
76
|
+
end
|
77
|
+
|
78
|
+
Backport of #9073
|
79
|
+
Fixes #8898
|
80
|
+
|
81
|
+
*Lilibeth De La Cruz*
|
82
|
+
|
83
|
+
* Fix counter cache columns not updated when replacing `has_many :through`
|
84
|
+
associations.
|
85
|
+
Backport #8400.
|
86
|
+
Fix #7630.
|
87
|
+
|
88
|
+
*Matthew Robertson*
|
89
|
+
|
90
|
+
* Don't update `column_defaults` when calling destructive methods on column with default value.
|
91
|
+
Backport c517602.
|
92
|
+
Fix #6115.
|
93
|
+
|
94
|
+
*Piotr Sarnacki + Aleksey Magusev + Alan Daud*
|
95
|
+
|
96
|
+
* When `#count` is used in conjunction with `#uniq` we perform `count(:distinct => true)`.
|
97
|
+
Fix #6865.
|
98
|
+
|
99
|
+
Example:
|
100
|
+
|
101
|
+
relation.uniq.count # => SELECT COUNT(DISTINCT *)
|
102
|
+
|
103
|
+
*Yves Senn + Kaspar Schiess*
|
104
|
+
|
105
|
+
* Fix `ActiveRecord::Relation#pluck` when columns or tables are reserved words.
|
106
|
+
Backport #7536.
|
107
|
+
Fix #8968.
|
108
|
+
|
109
|
+
*Ian Lesperance + Yves Senn + Kaspar Schiess*
|
110
|
+
|
111
|
+
* Don't run explain on slow queries for database adapters that don't support it.
|
112
|
+
Backport #6197.
|
113
|
+
|
114
|
+
*Blake Smith*
|
115
|
+
|
116
|
+
* Revert round usec when comparing timestamp attributes in the dirty tracking.
|
117
|
+
Fixes #8460.
|
118
|
+
|
119
|
+
*Andrew White*
|
120
|
+
|
121
|
+
* Revert creation of through association models when using `collection=[]`
|
122
|
+
on a `has_many :through` association from an unsaved model.
|
123
|
+
Fix #7661, #8269.
|
124
|
+
|
125
|
+
*Ernie Miller*
|
126
|
+
|
127
|
+
* Fix undefined method `to_i` when calling `new` on a scope that uses an
|
128
|
+
Array; Fix FloatDomainError when setting integer column to NaN.
|
129
|
+
Fixes #8718, #8734, #8757.
|
130
|
+
|
131
|
+
*Jason Stirk + Tristan Harward*
|
132
|
+
|
133
|
+
* Serialized attributes can be serialized in integer columns.
|
134
|
+
Fix #8575.
|
135
|
+
|
136
|
+
*Rafael Mendonça França*
|
137
|
+
|
138
|
+
* Keep index names when using `alter_table` with sqlite3.
|
139
|
+
Fix #3489.
|
140
|
+
Backport #8522.
|
141
|
+
|
142
|
+
*Yves Senn*
|
143
|
+
|
144
|
+
* Recognize migrations placed in directories containing numbers and 'rb'.
|
145
|
+
Fix #8492.
|
146
|
+
Backport of #8500.
|
147
|
+
|
148
|
+
*Yves Senn*
|
149
|
+
|
150
|
+
* Add `ActiveRecord::Base.cache_timestamp_format` class attribute to control
|
151
|
+
the format of the timestamp value in the cache key.
|
152
|
+
This allows users to improve the precision of the cache key.
|
153
|
+
Fixes #8195.
|
154
|
+
|
155
|
+
*Rafael Mendonça França*
|
156
|
+
|
157
|
+
* Add `:nsec` date format. This can be used to improve the precision of cache key.
|
158
|
+
Please note that this format only works with Ruby 1.9, Ruby 1.8 will ignore it completely.
|
159
|
+
|
160
|
+
*Jamie Gaskins*
|
161
|
+
|
162
|
+
* Unscope `update_column(s)` query to ignore default scope.
|
163
|
+
|
164
|
+
When applying `default_scope` to a class with a where clause, using
|
165
|
+
`update_column(s)` could generate a query that would not properly update
|
166
|
+
the record due to the where clause from the `default_scope` being applied
|
167
|
+
to the update query.
|
168
|
+
|
169
|
+
class User < ActiveRecord::Base
|
170
|
+
default_scope where(active: true)
|
171
|
+
end
|
172
|
+
|
173
|
+
user = User.first
|
174
|
+
user.active = false
|
175
|
+
user.save!
|
176
|
+
|
177
|
+
user.update_column(:active, true) # => false
|
178
|
+
|
179
|
+
In this situation we want to skip the default_scope clause and just
|
180
|
+
update the record based on the primary key. With this change:
|
181
|
+
|
182
|
+
user.update_column(:active, true) # => true
|
183
|
+
|
184
|
+
Backport of #8436 fix.
|
185
|
+
|
186
|
+
*Carlos Antonio da Silva*
|
187
|
+
|
188
|
+
* Fix performance problem with primary_key method in PostgreSQL adapter when having many schemas.
|
189
|
+
Uses pg_constraint table instead of pg_depend table which has many records in general.
|
190
|
+
Fix #8414
|
191
|
+
|
192
|
+
*kennyj*
|
193
|
+
|
194
|
+
* Do not instantiate intermediate Active Record objects when eager loading.
|
195
|
+
These records caused `after_find` to run more than expected.
|
196
|
+
Fix #3313
|
197
|
+
Backport of #8403
|
198
|
+
|
199
|
+
*Yves Senn*
|
200
|
+
|
201
|
+
* Fix `pluck` to work with joins. Backport of #4942.
|
202
|
+
|
203
|
+
*Carlos Antonio da Silva*
|
204
|
+
|
205
|
+
* Fix a problem with `translate_exception` method in a non English environment.
|
206
|
+
Backport of #6397.
|
207
|
+
|
208
|
+
*kennyj*
|
209
|
+
|
210
|
+
* Fix dirty attribute checks for TimeZoneConversion with nil and blank
|
211
|
+
datetime attributes. Setting a nil datetime to a blank string should not
|
212
|
+
result in a change being flagged.
|
213
|
+
Fixes #8310.
|
214
|
+
Backport of #8311.
|
215
|
+
|
216
|
+
*Alisdair McDiarmid*
|
217
|
+
|
218
|
+
* Prevent mass assignment to the type column of polymorphic associations when using `build`.
|
219
|
+
Fixes #8265.
|
220
|
+
Backport of #8291.
|
221
|
+
|
222
|
+
*Yves Senn*
|
223
|
+
|
224
|
+
* When running migrations on Postgresql, the `:limit` option for `binary` and `text` columns is
|
225
|
+
silently dropped.
|
226
|
+
Previously, these migrations caused sql exceptions, because Postgresql doesn't support limits
|
227
|
+
on these types.
|
228
|
+
|
229
|
+
*Victor Costan*
|
230
|
+
|
231
|
+
* `#pluck` can be used on a relation with `select` clause.
|
232
|
+
Fixes #7551.
|
233
|
+
Backport of #8176.
|
234
|
+
|
235
|
+
Example:
|
236
|
+
|
237
|
+
Topic.select([:approved, :id]).order(:id).pluck(:id)
|
238
|
+
|
239
|
+
*Yves Senn*
|
240
|
+
|
241
|
+
* Use `nil?` instead of `blank?` to check whether dynamic finder with a bang
|
242
|
+
should raise RecordNotFound.
|
243
|
+
Fixes #7238.
|
244
|
+
|
245
|
+
*Nikita Afanasenko*
|
246
|
+
|
247
|
+
* Fix deleting from a HABTM join table upon destroying an object of a model
|
248
|
+
with optimistic locking enabled.
|
249
|
+
Fixes #5332.
|
250
|
+
|
251
|
+
*Nick Rogers*
|
252
|
+
|
253
|
+
* Use query cache/uncache when using ENV["DATABASE_URL"].
|
254
|
+
Fixes #6951.
|
255
|
+
Backport of #8074.
|
256
|
+
|
257
|
+
*kennyj*
|
258
|
+
|
259
|
+
* Do not create useless database transaction when building `has_one` association.
|
260
|
+
|
261
|
+
Example:
|
262
|
+
|
263
|
+
User.has_one :profile
|
264
|
+
User.new.build_profile
|
265
|
+
|
266
|
+
Backport of #8154.
|
267
|
+
|
268
|
+
*Bogdan Gusiev*
|
269
|
+
|
270
|
+
* `AR::Base#attributes_before_type_cast` now returns unserialized values for serialized attributes.
|
271
|
+
|
272
|
+
*Nikita Afanasenko*
|
273
|
+
|
274
|
+
* Fix issue that raises `NameError` when overriding the `accepts_nested_attributes` in child classes.
|
275
|
+
|
276
|
+
Before:
|
277
|
+
|
278
|
+
class Shared::Person < ActiveRecord::Base
|
279
|
+
has_one :address
|
280
|
+
|
281
|
+
accepts_nested_attributes :address, :reject_if => :all_blank
|
282
|
+
end
|
283
|
+
|
284
|
+
class Person < Shared::Person
|
285
|
+
accepts_nested_attributes :address
|
286
|
+
end
|
287
|
+
|
288
|
+
Person
|
289
|
+
#=> NameError: method `address_attributes=' not defined in Person
|
290
|
+
|
291
|
+
After:
|
292
|
+
|
293
|
+
Person
|
294
|
+
#=> Person(id: integer, ...)
|
295
|
+
|
296
|
+
Fixes #8131.
|
297
|
+
|
298
|
+
*Gabriel Sobrinho, Ricardo Henrique*
|
299
|
+
|
300
|
+
|
301
|
+
## Rails 3.2.12 (Feb 11, 2013) ##
|
2
302
|
|
3
303
|
* Quote numeric values being compared to non-numeric columns. Otherwise,
|
4
304
|
in some database, the string column values will be coerced to a numeric
|
@@ -10,17 +310,24 @@
|
|
10
310
|
|
11
311
|
*Dylan Smith*
|
12
312
|
|
313
|
+
|
13
314
|
## Rails 3.2.11 (Jan 8, 2013) ##
|
14
315
|
|
15
316
|
* Fix querying with an empty hash *Damien Mathieu* [CVE-2013-0155]
|
16
317
|
|
17
|
-
|
318
|
+
|
319
|
+
## Rails 3.2.10 (Jan 2, 2013) ##
|
18
320
|
|
19
321
|
* CVE-2012-5664 options hashes should only be extracted if there are extra
|
20
322
|
parameters
|
21
323
|
|
324
|
+
|
22
325
|
## Rails 3.2.9 (Nov 12, 2012) ##
|
23
326
|
|
327
|
+
* Fix `find_in_batches` crashing when IDs are strings and start option is not specified.
|
328
|
+
|
329
|
+
*Alexis Bernard*
|
330
|
+
|
24
331
|
* Fix issue with collection associations calling first(n)/last(n) and attempting
|
25
332
|
to set the inverse association when `:inverse_of` was used. Fixes #8087.
|
26
333
|
|
@@ -231,7 +231,8 @@ module ActiveRecord
|
|
231
231
|
|
232
232
|
def build_record(attributes, options)
|
233
233
|
reflection.build_association(attributes, options) do |record|
|
234
|
-
|
234
|
+
skip_assign = [reflection.foreign_key, reflection.type].compact
|
235
|
+
attributes = create_scope.except(*(record.changed - skip_assign))
|
235
236
|
record.assign_attributes(attributes, :without_protection => true)
|
236
237
|
end
|
237
238
|
end
|
@@ -38,20 +38,6 @@ module ActiveRecord
|
|
38
38
|
super
|
39
39
|
end
|
40
40
|
|
41
|
-
def concat_records(records)
|
42
|
-
ensure_not_nested
|
43
|
-
|
44
|
-
records = super
|
45
|
-
|
46
|
-
if owner.new_record? && records
|
47
|
-
records.flatten.each do |record|
|
48
|
-
build_through_record(record)
|
49
|
-
end
|
50
|
-
end
|
51
|
-
|
52
|
-
records
|
53
|
-
end
|
54
|
-
|
55
41
|
def insert_record(record, validate = true, raise = false)
|
56
42
|
ensure_not_nested
|
57
43
|
|
@@ -153,6 +139,11 @@ module ActiveRecord
|
|
153
139
|
|
154
140
|
delete_through_records(records)
|
155
141
|
|
142
|
+
if source_reflection.options[:counter_cache]
|
143
|
+
counter = source_reflection.counter_cache_column
|
144
|
+
klass.decrement_counter counter, records.map(&:id)
|
145
|
+
end
|
146
|
+
|
156
147
|
if through_reflection.macro == :has_many && update_through_counter?(method)
|
157
148
|
update_counter(-count, through_reflection)
|
158
149
|
end
|
@@ -11,7 +11,7 @@ module ActiveRecord
|
|
11
11
|
# If target and record are nil, or target is equal to record,
|
12
12
|
# we don't need to have transaction.
|
13
13
|
if (target || record) && target != record
|
14
|
-
|
14
|
+
transaction_if(save) do
|
15
15
|
remove_target!(options[:dependent]) if target && !target.destroyed?
|
16
16
|
|
17
17
|
if record
|
@@ -70,6 +70,14 @@ module ActiveRecord
|
|
70
70
|
def nullify_owner_attributes(record)
|
71
71
|
record[reflection.foreign_key] = nil
|
72
72
|
end
|
73
|
+
|
74
|
+
def transaction_if(value)
|
75
|
+
if value
|
76
|
+
reflection.klass.transaction { yield }
|
77
|
+
else
|
78
|
+
yield
|
79
|
+
end
|
80
|
+
end
|
73
81
|
end
|
74
82
|
end
|
75
83
|
end
|
@@ -37,7 +37,8 @@ module ActiveRecord
|
|
37
37
|
through_records = Array.wrap(owner.send(through_reflection.name))
|
38
38
|
|
39
39
|
# Dont cache the association - we would only be caching a subset
|
40
|
-
if
|
40
|
+
if (preload_options != through_options) ||
|
41
|
+
(reflection.options[:source_type] && through_reflection.collection?)
|
41
42
|
owner.association(through_reflection.name).reset
|
42
43
|
end
|
43
44
|
|
@@ -90,6 +90,14 @@ module ActiveRecord
|
|
90
90
|
end
|
91
91
|
end
|
92
92
|
|
93
|
+
def _field_changed?(attr, old, value)
|
94
|
+
if self.class.serialized_attributes.include?(attr)
|
95
|
+
old != value
|
96
|
+
else
|
97
|
+
super
|
98
|
+
end
|
99
|
+
end
|
100
|
+
|
93
101
|
def read_attribute_before_type_cast(attr_name)
|
94
102
|
if serialized_attributes.include?(attr_name)
|
95
103
|
super.unserialized_value
|
@@ -97,6 +105,16 @@ module ActiveRecord
|
|
97
105
|
super
|
98
106
|
end
|
99
107
|
end
|
108
|
+
|
109
|
+
def attributes_before_type_cast
|
110
|
+
super.dup.tap do |attributes|
|
111
|
+
self.class.serialized_attributes.each_key do |key|
|
112
|
+
if attributes.key?(key)
|
113
|
+
attributes[key] = attributes[key].unserialized_value
|
114
|
+
end
|
115
|
+
end
|
116
|
+
end
|
117
|
+
end
|
100
118
|
end
|
101
119
|
end
|
102
120
|
end
|
@@ -37,18 +37,16 @@ module ActiveRecord
|
|
37
37
|
if create_time_zone_conversion_attribute?(attr_name, columns_hash[attr_name])
|
38
38
|
method_body, line = <<-EOV, __LINE__ + 1
|
39
39
|
def #{attr_name}=(original_time)
|
40
|
+
original_time = nil if original_time.blank?
|
40
41
|
time = original_time
|
41
42
|
unless time.acts_like?(:time)
|
42
43
|
time = time.is_a?(String) ? Time.zone.parse(time) : time.to_time rescue time
|
43
44
|
end
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
if
|
48
|
-
|
49
|
-
#{attr_name}_will_change!
|
50
|
-
@attributes_cache["#{attr_name}"] = zoned_time
|
51
|
-
end
|
45
|
+
time = time.in_time_zone rescue nil if time
|
46
|
+
previous_time = attribute_changed?("#{attr_name}") ? changed_attributes["#{attr_name}"] : read_attribute(:#{attr_name})
|
47
|
+
write_attribute(:#{attr_name}, original_time)
|
48
|
+
#{attr_name}_will_change! if previous_time != time
|
49
|
+
@attributes_cache["#{attr_name}"] = time
|
52
50
|
end
|
53
51
|
EOV
|
54
52
|
generated_attribute_methods.module_eval(method_body, __FILE__, line)
|
@@ -62,12 +60,6 @@ module ActiveRecord
|
|
62
60
|
time_zone_aware_attributes && !self.skip_time_zone_conversion_for_attributes.include?(name.to_sym) && column.type.in?([:datetime, :timestamp])
|
63
61
|
end
|
64
62
|
end
|
65
|
-
|
66
|
-
private
|
67
|
-
def round_usec(value)
|
68
|
-
return unless value
|
69
|
-
value.change(:usec => 0)
|
70
|
-
end
|
71
63
|
end
|
72
64
|
end
|
73
65
|
end
|
@@ -54,12 +54,13 @@ module ActiveRecord
|
|
54
54
|
end
|
55
55
|
|
56
56
|
def convert_number_column_value(value)
|
57
|
-
|
57
|
+
case value
|
58
|
+
when FalseClass
|
58
59
|
0
|
59
|
-
|
60
|
+
when TrueClass
|
60
61
|
1
|
61
|
-
|
62
|
-
|
62
|
+
when String
|
63
|
+
value.presence
|
63
64
|
else
|
64
65
|
value
|
65
66
|
end
|
data/lib/active_record/base.rb
CHANGED
@@ -479,7 +479,8 @@ module ActiveRecord #:nodoc:
|
|
479
479
|
# # Instantiates a single new object bypassing mass-assignment security
|
480
480
|
# User.new({ :first_name => 'Jamie', :is_admin => true }, :without_protection => true)
|
481
481
|
def initialize(attributes = nil, options = {})
|
482
|
-
|
482
|
+
defaults = Hash[self.class.column_defaults.map { |k, v| [k, v.duplicable? ? v.dup : v] }]
|
483
|
+
@attributes = self.class.initialize_attributes(defaults)
|
483
484
|
@association_cache = {}
|
484
485
|
@aggregation_cache = {}
|
485
486
|
@attributes_cache = {}
|
@@ -552,12 +553,11 @@ module ActiveRecord #:nodoc:
|
|
552
553
|
@new_record = true
|
553
554
|
|
554
555
|
ensure_proper_type
|
555
|
-
populate_with_current_scope_attributes
|
556
556
|
super
|
557
557
|
end
|
558
558
|
|
559
559
|
# Backport dup from 1.9 so that initialize_dup() gets called
|
560
|
-
unless Object.respond_to?(:initialize_dup)
|
560
|
+
unless Object.respond_to?(:initialize_dup, true)
|
561
561
|
def dup # :nodoc:
|
562
562
|
copy = super
|
563
563
|
copy.initialize_dup(self)
|
@@ -266,7 +266,7 @@ module ActiveRecord
|
|
266
266
|
# Inserts the given fixture into the table. Overridden in adapters that require
|
267
267
|
# something beyond a simple insert (eg. Oracle).
|
268
268
|
def insert_fixture(fixture, table_name)
|
269
|
-
columns =
|
269
|
+
columns = schema_cache.columns_hash(table_name)
|
270
270
|
|
271
271
|
key_list = []
|
272
272
|
value_list = fixture.map do |name, value|
|
@@ -25,19 +25,13 @@ module ActiveRecord
|
|
25
25
|
when true, false
|
26
26
|
if column && column.type == :integer
|
27
27
|
value ? '1' : '0'
|
28
|
-
elsif column && [:text, :string, :binary].include?(column.type)
|
29
|
-
value ? "'1'" : "'0'"
|
30
28
|
else
|
31
29
|
value ? quoted_true : quoted_false
|
32
30
|
end
|
33
31
|
# BigDecimals need to be put in a non-normalized form and quoted.
|
34
32
|
when nil then "NULL"
|
35
|
-
when
|
36
|
-
|
37
|
-
if column && ![:integer, :float, :decimal].include?(column.type)
|
38
|
-
value = "'#{value}'"
|
39
|
-
end
|
40
|
-
value
|
33
|
+
when BigDecimal then value.to_s('F')
|
34
|
+
when Numeric then value.to_s
|
41
35
|
when Date, Time then "'#{quoted_date(value)}'"
|
42
36
|
when Symbol then "'#{quote_string(value.to_s)}'"
|
43
37
|
else
|
@@ -199,6 +199,8 @@ module ActiveRecord
|
|
199
199
|
if value.kind_of?(String) && column && column.type == :binary && column.class.respond_to?(:string_to_binary)
|
200
200
|
s = column.class.string_to_binary(value).unpack("H*")[0]
|
201
201
|
"x'#{s}'"
|
202
|
+
elsif value.kind_of?(BigDecimal)
|
203
|
+
value.to_s("F")
|
202
204
|
else
|
203
205
|
super
|
204
206
|
end
|
@@ -315,8 +315,6 @@ module ActiveRecord
|
|
315
315
|
@visitor = BindSubstitution.new self
|
316
316
|
end
|
317
317
|
|
318
|
-
connection_parameters.delete :prepared_statements
|
319
|
-
|
320
318
|
@connection_parameters, @config = connection_parameters, config
|
321
319
|
|
322
320
|
# @local_tz is initialized as nil to avoid warnings when connect tries to use it
|
@@ -988,12 +986,11 @@ module ActiveRecord
|
|
988
986
|
# Returns just a table's primary key
|
989
987
|
def primary_key(table)
|
990
988
|
row = exec_query(<<-end_sql, 'SCHEMA').rows.first
|
991
|
-
SELECT
|
989
|
+
SELECT attr.attname
|
992
990
|
FROM pg_attribute attr
|
993
|
-
INNER JOIN pg_depend dep ON attr.attrelid = dep.refobjid AND attr.attnum = dep.refobjsubid
|
994
991
|
INNER JOIN pg_constraint cons ON attr.attrelid = cons.conrelid AND attr.attnum = cons.conkey[1]
|
995
992
|
WHERE cons.contype = 'p'
|
996
|
-
AND
|
993
|
+
AND cons.conrelid = '#{quote_table_name(table)}'::regclass
|
997
994
|
end_sql
|
998
995
|
|
999
996
|
row && row.first
|
@@ -1078,6 +1075,13 @@ module ActiveRecord
|
|
1078
1075
|
when nil, 0..0x3fffffff; super(type)
|
1079
1076
|
else raise(ActiveRecordError, "No binary type has byte size #{limit}.")
|
1080
1077
|
end
|
1078
|
+
when 'text'
|
1079
|
+
# PostgreSQL doesn't support limits on text columns.
|
1080
|
+
# The hard limit is 1Gb, according to section 8.3 in the manual.
|
1081
|
+
case limit
|
1082
|
+
when nil, 0..0x3fffffff; super(type)
|
1083
|
+
else raise(ActiveRecordError, "The limit on text can be at most 1GB - 1byte.")
|
1084
|
+
end
|
1081
1085
|
when 'integer'
|
1082
1086
|
return 'integer' unless limit
|
1083
1087
|
|
@@ -1135,11 +1139,15 @@ module ActiveRecord
|
|
1135
1139
|
@connection.server_version
|
1136
1140
|
end
|
1137
1141
|
|
1142
|
+
# See http://www.postgresql.org/docs/9.1/static/errcodes-appendix.html
|
1143
|
+
FOREIGN_KEY_VIOLATION = "23503"
|
1144
|
+
UNIQUE_VIOLATION = "23505"
|
1145
|
+
|
1138
1146
|
def translate_exception(exception, message)
|
1139
|
-
case exception.
|
1140
|
-
when
|
1147
|
+
case exception.result.error_field(PGresult::PG_DIAG_SQLSTATE)
|
1148
|
+
when UNIQUE_VIOLATION
|
1141
1149
|
RecordNotUnique.new(message, exception)
|
1142
|
-
when
|
1150
|
+
when FOREIGN_KEY_VIOLATION
|
1143
1151
|
InvalidForeignKey.new(message, exception)
|
1144
1152
|
else
|
1145
1153
|
super
|
@@ -1,7 +1,7 @@
|
|
1
1
|
module ActiveRecord
|
2
2
|
module ConnectionAdapters
|
3
3
|
class SchemaCache
|
4
|
-
attr_reader :
|
4
|
+
attr_reader :primary_keys, :tables
|
5
5
|
attr_reader :connection
|
6
6
|
|
7
7
|
def initialize(conn)
|
@@ -30,6 +30,25 @@ module ActiveRecord
|
|
30
30
|
@tables[name] = connection.table_exists?(name)
|
31
31
|
end
|
32
32
|
|
33
|
+
# Get the columns for a table
|
34
|
+
def columns(table = nil)
|
35
|
+
if table
|
36
|
+
@columns[table]
|
37
|
+
else
|
38
|
+
@columns
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
# Get the columns for a table as a hash, key is the column name
|
43
|
+
# value is the column object.
|
44
|
+
def columns_hash(table = nil)
|
45
|
+
if table
|
46
|
+
@columns_hash[table]
|
47
|
+
else
|
48
|
+
@columns_hash
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
33
52
|
# Clears out internal caches
|
34
53
|
def clear!
|
35
54
|
@columns.clear
|
@@ -490,7 +490,11 @@ module ActiveRecord
|
|
490
490
|
end
|
491
491
|
|
492
492
|
def copy_table(from, to, options = {}) #:nodoc:
|
493
|
-
|
493
|
+
from_primary_key = primary_key(from)
|
494
|
+
options[:primary_key] = from_primary_key if from_primary_key != 'id'
|
495
|
+
unless options[:primary_key]
|
496
|
+
options[:id] = !columns(from).detect{|c| c.name == 'id'}.nil? && 'id' == from_primary_key
|
497
|
+
end
|
494
498
|
create_table(to, options) do |definition|
|
495
499
|
@definition = definition
|
496
500
|
columns(from).each do |column|
|
@@ -504,7 +508,7 @@ module ActiveRecord
|
|
504
508
|
:precision => column.precision, :scale => column.scale,
|
505
509
|
:null => column.null)
|
506
510
|
end
|
507
|
-
@definition.primary_key(
|
511
|
+
@definition.primary_key(from_primary_key) if from_primary_key
|
508
512
|
yield @definition if block_given?
|
509
513
|
end
|
510
514
|
|
@@ -530,7 +534,7 @@ module ActiveRecord
|
|
530
534
|
|
531
535
|
unless columns.empty?
|
532
536
|
# index name can't be the same
|
533
|
-
opts = { :name => name.gsub(/_(#{from})_/, "
|
537
|
+
opts = { :name => name.gsub(/(^|_)(#{from})_/, "\\1#{to}_") }
|
534
538
|
opts[:unique] = true if index.unique
|
535
539
|
add_index(to, columns, opts)
|
536
540
|
end
|
@@ -11,11 +11,12 @@ module ActiveRecord
|
|
11
11
|
end
|
12
12
|
end
|
13
13
|
|
14
|
-
# If
|
15
|
-
#
|
16
|
-
#
|
17
|
-
#
|
18
|
-
# convenient for relations.
|
14
|
+
# If the database adapter supports explain and auto explain is enabled,
|
15
|
+
# this method triggers EXPLAIN logging for the queries triggered by the
|
16
|
+
# block if it takes more than the threshold as a whole. That is, the
|
17
|
+
# threshold is not checked against each individual query, but against the
|
18
|
+
# duration of the entire block. This approach is convenient for relations.
|
19
|
+
|
19
20
|
#
|
20
21
|
# The available_queries_for_explain thread variable collects the queries
|
21
22
|
# to be explained. If the value is nil, it means queries are not being
|
@@ -26,7 +27,7 @@ module ActiveRecord
|
|
26
27
|
|
27
28
|
threshold = auto_explain_threshold_in_seconds
|
28
29
|
current = Thread.current
|
29
|
-
if threshold && current[:available_queries_for_explain].nil?
|
30
|
+
if connection.supports_explain? && threshold && current[:available_queries_for_explain].nil?
|
30
31
|
begin
|
31
32
|
queries = current[:available_queries_for_explain] = []
|
32
33
|
start = Time.now
|
@@ -1,5 +1,16 @@
|
|
1
1
|
module ActiveRecord
|
2
2
|
module Integration
|
3
|
+
extend ActiveSupport::Concern
|
4
|
+
|
5
|
+
included do
|
6
|
+
##
|
7
|
+
# :singleton-method:
|
8
|
+
# Indicates the format used to generate the timestamp format in the cache key.
|
9
|
+
# This is +:number+, by default.
|
10
|
+
class_attribute :cache_timestamp_format, :instance_writer => false
|
11
|
+
self.cache_timestamp_format = :number
|
12
|
+
end
|
13
|
+
|
3
14
|
# Returns a String, which Action Pack uses for constructing an URL to this
|
4
15
|
# object. The default implementation returns this record's id as a String,
|
5
16
|
# or nil if this record's unsaved.
|
@@ -39,7 +50,7 @@ module ActiveRecord
|
|
39
50
|
when new_record?
|
40
51
|
"#{self.class.model_name.cache_key}/new"
|
41
52
|
when timestamp = self[:updated_at]
|
42
|
-
timestamp = timestamp.utc.to_s(
|
53
|
+
timestamp = timestamp.utc.to_s(cache_timestamp_format)
|
43
54
|
"#{self.class.model_name.cache_key}/#{id}-#{timestamp}"
|
44
55
|
else
|
45
56
|
"#{self.class.model_name.cache_key}/#{id}"
|
@@ -458,7 +458,7 @@ module ActiveRecord
|
|
458
458
|
say_with_time "#{method}(#{arg_list})" do
|
459
459
|
unless reverting?
|
460
460
|
unless arguments.empty? || method == :execute
|
461
|
-
arguments[0] = Migrator.proper_table_name(arguments.first)
|
461
|
+
arguments[0] = Migrator.proper_table_name(arguments.first) unless method == :assume_migrated_upto_version
|
462
462
|
arguments[1] = Migrator.proper_table_name(arguments.second) if method == :rename_table
|
463
463
|
end
|
464
464
|
end
|
@@ -627,7 +627,7 @@ module ActiveRecord
|
|
627
627
|
seen = Hash.new false
|
628
628
|
|
629
629
|
migrations = files.map do |file|
|
630
|
-
version, name, scope = file.scan(/([0-9]+)_([_a-z0-9]*)\.?([_a-z0-9]*)
|
630
|
+
version, name, scope = file.scan(/([0-9]+)_([_a-z0-9]*)\.?([_a-z0-9]*)?\.rb\z/).first
|
631
631
|
|
632
632
|
raise IllegalMigrationNameError.new(file) unless version
|
633
633
|
version = version.to_i
|
@@ -277,13 +277,14 @@ module ActiveRecord
|
|
277
277
|
|
278
278
|
type = (reflection.collection? ? :collection : :one_to_one)
|
279
279
|
|
280
|
+
# remove_possible_method :pirate_attributes=
|
281
|
+
#
|
280
282
|
# def pirate_attributes=(attributes)
|
281
283
|
# assign_nested_attributes_for_one_to_one_association(:pirate, attributes, mass_assignment_options)
|
282
284
|
# end
|
283
285
|
class_eval <<-eoruby, __FILE__, __LINE__ + 1
|
284
|
-
|
285
|
-
|
286
|
-
end
|
286
|
+
remove_possible_method(:#{association_name}_attributes=)
|
287
|
+
|
287
288
|
def #{association_name}_attributes=(attributes)
|
288
289
|
assign_nested_attributes_for_#{type}_association(:#{association_name}, attributes, mass_assignment_options)
|
289
290
|
end
|
@@ -194,7 +194,7 @@ module ActiveRecord
|
|
194
194
|
raise ActiveRecordError, "#{name} is marked as readonly" if self.class.readonly_attributes.include?(name)
|
195
195
|
raise ActiveRecordError, "can not update on a new record object" unless persisted?
|
196
196
|
|
197
|
-
updated_count = self.class.update_all({ name => value }, self.class.primary_key => id)
|
197
|
+
updated_count = self.class.unscoped.update_all({ name => value }, self.class.primary_key => id)
|
198
198
|
|
199
199
|
raw_write_attribute(name, value)
|
200
200
|
|
@@ -6,19 +6,19 @@ module ActiveRecord
|
|
6
6
|
module ClassMethods
|
7
7
|
# Enable the query cache within the block if Active Record is configured.
|
8
8
|
def cache(&block)
|
9
|
-
if ActiveRecord::Base.
|
10
|
-
yield
|
11
|
-
else
|
9
|
+
if ActiveRecord::Base.connected?
|
12
10
|
connection.cache(&block)
|
11
|
+
else
|
12
|
+
yield
|
13
13
|
end
|
14
14
|
end
|
15
15
|
|
16
16
|
# Disable the query cache within the block if Active Record is configured.
|
17
17
|
def uncached(&block)
|
18
|
-
if ActiveRecord::Base.
|
19
|
-
yield
|
20
|
-
else
|
18
|
+
if ActiveRecord::Base.connected?
|
21
19
|
connection.uncached(&block)
|
20
|
+
else
|
21
|
+
yield
|
22
22
|
end
|
23
23
|
end
|
24
24
|
end
|
@@ -83,6 +83,13 @@ module ActiveRecord
|
|
83
83
|
end
|
84
84
|
end
|
85
85
|
|
86
|
+
initializer "active_record.validate_explain_support" do |app|
|
87
|
+
if app.config.active_record[:auto_explain_threshold_in_seconds] &&
|
88
|
+
!ActiveRecord::Base.connection.supports_explain?
|
89
|
+
warn "auto_explain_threshold_in_seconds is set but will be ignored because your adapter does not support this feature. Please unset the configuration to avoid this warning."
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
86
93
|
# Expose database runtime to controller for logging.
|
87
94
|
initializer "active_record.log_runtime" do |app|
|
88
95
|
require "active_record/railties/controller_runtime"
|
@@ -64,10 +64,21 @@ db_namespace = namespace :db do
|
|
64
64
|
end
|
65
65
|
end
|
66
66
|
|
67
|
+
# If neither encoding nor collation is specified, use the utf-8 defaults.
|
67
68
|
def mysql_creation_options(config)
|
68
|
-
|
69
|
-
|
70
|
-
|
69
|
+
default_charset = ENV['CHARSET'] || 'utf8'
|
70
|
+
default_collation = ENV['COLLATION'] || 'utf8_unicode_ci'
|
71
|
+
|
72
|
+
Hash.new.tap do |options|
|
73
|
+
options[:charset] = config['encoding'] if config.include? 'encoding'
|
74
|
+
options[:collation] = config['collation'] if config.include? 'collation'
|
75
|
+
|
76
|
+
# Set default charset only when collation isn't set.
|
77
|
+
options[:charset] ||= default_charset unless options[:collation]
|
78
|
+
|
79
|
+
# Set default collation only when charset is also default.
|
80
|
+
options[:collation] ||= default_collation if options[:charset] == default_charset
|
81
|
+
end
|
71
82
|
end
|
72
83
|
|
73
84
|
def create_database(config)
|
@@ -101,9 +112,12 @@ db_namespace = namespace :db do
|
|
101
112
|
error_class = config['adapter'] =~ /mysql2/ ? Mysql2::Error : Mysql::Error
|
102
113
|
end
|
103
114
|
access_denied_error = 1045
|
115
|
+
|
116
|
+
create_options = mysql_creation_options(config)
|
117
|
+
|
104
118
|
begin
|
105
119
|
ActiveRecord::Base.establish_connection(config.merge('database' => nil))
|
106
|
-
ActiveRecord::Base.connection.create_database(config['database'],
|
120
|
+
ActiveRecord::Base.connection.create_database(config['database'], create_options)
|
107
121
|
ActiveRecord::Base.establish_connection(config)
|
108
122
|
rescue error_class => sqlerr
|
109
123
|
if sqlerr.errno == access_denied_error
|
@@ -119,7 +133,7 @@ db_namespace = namespace :db do
|
|
119
133
|
ActiveRecord::Base.establish_connection(config)
|
120
134
|
else
|
121
135
|
$stderr.puts sqlerr.error
|
122
|
-
$stderr.puts "Couldn't create database for #{config.inspect}, charset: #{
|
136
|
+
$stderr.puts "Couldn't create database for #{config.inspect}, charset: #{create_options[:charset]}, collation: #{create_options[:collation]}"
|
123
137
|
$stderr.puts "(if you set the charset manually, make sure you have a matching collation)" if config['encoding']
|
124
138
|
end
|
125
139
|
end
|
@@ -419,11 +433,11 @@ db_namespace = namespace :db do
|
|
419
433
|
when 'sqlserver'
|
420
434
|
`smoscript -s #{config['host']} -d #{config['database']} -u #{config['username']} -p #{config['password']} -f #{filename} -A -U`
|
421
435
|
when "firebird"
|
422
|
-
set_firebird_env(
|
423
|
-
db_string = firebird_db_string(
|
436
|
+
set_firebird_env(config)
|
437
|
+
db_string = firebird_db_string(config)
|
424
438
|
sh "isql -a #{db_string} > #{filename}"
|
425
439
|
else
|
426
|
-
raise "Task not supported by '#{
|
440
|
+
raise "Task not supported by '#{config['adapter']}'"
|
427
441
|
end
|
428
442
|
|
429
443
|
if ActiveRecord::Base.connection.supports_migrations?
|
@@ -59,11 +59,11 @@ module ActiveRecord
|
|
59
59
|
relation = apply_finder_options(finder_options)
|
60
60
|
end
|
61
61
|
|
62
|
-
start = options.delete(:start)
|
62
|
+
start = options.delete(:start)
|
63
63
|
batch_size = options.delete(:batch_size) || 1000
|
64
64
|
|
65
65
|
relation = relation.reorder(batch_order).limit(batch_size)
|
66
|
-
records = relation.where(table[primary_key].gteq(start)).
|
66
|
+
records = start ? relation.where(table[primary_key].gteq(start)).to_a : relation.to_a
|
67
67
|
|
68
68
|
while records.any?
|
69
69
|
records_size = records.size
|
@@ -177,8 +177,15 @@ module ActiveRecord
|
|
177
177
|
# Person.where(:confirmed => true).limit(5).pluck(:id)
|
178
178
|
#
|
179
179
|
def pluck(column_name)
|
180
|
-
column_name
|
181
|
-
|
180
|
+
if column_name.is_a?(Symbol) && column_names.include?(column_name.to_s)
|
181
|
+
column_name = "#{connection.quote_table_name(table_name)}.#{connection.quote_column_name(column_name)}"
|
182
|
+
else
|
183
|
+
column_name = column_name.to_s
|
184
|
+
end
|
185
|
+
|
186
|
+
relation = clone
|
187
|
+
relation.select_values = [column_name]
|
188
|
+
klass.connection.select_all(relation.arel).map! do |attributes|
|
182
189
|
klass.type_cast_attribute(attributes.keys.first, klass.initialize_attributes(attributes))
|
183
190
|
end
|
184
191
|
end
|
@@ -188,7 +195,8 @@ module ActiveRecord
|
|
188
195
|
def perform_calculation(operation, column_name, options = {})
|
189
196
|
operation = operation.to_s.downcase
|
190
197
|
|
191
|
-
distinct
|
198
|
+
# If #count is used in conjuction with #uniq it is considered distinct. (eg. relation.uniq.count)
|
199
|
+
distinct = options[:distinct] || self.uniq_value
|
192
200
|
|
193
201
|
if operation == "count"
|
194
202
|
column_name ||= (select_for_count || :all)
|
@@ -253,9 +253,11 @@ module ActiveRecord
|
|
253
253
|
orders = relation.order_values.map { |val| val.presence }.compact
|
254
254
|
values = @klass.connection.distinct("#{@klass.connection.quote_table_name table_name}.#{primary_key}", orders)
|
255
255
|
|
256
|
-
relation = relation.dup
|
256
|
+
relation = relation.dup.select(values)
|
257
|
+
|
258
|
+
id_rows = @klass.connection.select_all(relation.arel, 'SQL', relation.bind_values)
|
259
|
+
ids_array = id_rows.map {|row| row[primary_key]}
|
257
260
|
|
258
|
-
ids_array = relation.select(values).collect {|row| row[primary_key]}
|
259
261
|
ids_array.empty? ? raise(ThrowResult) : table[primary_key].in(ids_array)
|
260
262
|
end
|
261
263
|
|
@@ -263,7 +265,7 @@ module ActiveRecord
|
|
263
265
|
conditions = Hash[attributes.map {|a| [a, args[attributes.index(a)]]}]
|
264
266
|
result = where(conditions).send(match.finder)
|
265
267
|
|
266
|
-
if match.bang? && result.
|
268
|
+
if match.bang? && result.nil?
|
267
269
|
raise RecordNotFound, "Couldn't find #{@klass.name} with #{conditions.to_a.collect {|p| p.join(' = ')}.join(', ')}"
|
268
270
|
else
|
269
271
|
yield(result) if block_given?
|
@@ -51,10 +51,6 @@ module ActiveRecord
|
|
51
51
|
when Class
|
52
52
|
# FIXME: I think we need to deprecate this behavior
|
53
53
|
attribute.eq(value.name)
|
54
|
-
when Integer, ActiveSupport::Duration
|
55
|
-
# Arel treats integers as literals, but they should be quoted when compared with strings
|
56
|
-
column = engine.connection.schema_cache.columns_hash[table.name][attribute.name.to_s]
|
57
|
-
attribute.eq(Arel::Nodes::SqlLiteral.new(engine.connection.quote(value, column)))
|
58
54
|
else
|
59
55
|
attribute.eq(value)
|
60
56
|
end
|
@@ -161,16 +161,14 @@ module ActiveRecord
|
|
161
161
|
# end
|
162
162
|
#
|
163
163
|
# def self.titles
|
164
|
-
#
|
164
|
+
# pluck(:title)
|
165
165
|
# end
|
166
|
-
#
|
167
166
|
# end
|
168
167
|
#
|
169
168
|
# We are able to call the methods like this:
|
170
169
|
#
|
171
170
|
# Article.published.featured.latest_article
|
172
171
|
# Article.featured.titles
|
173
|
-
|
174
172
|
def scope(name, scope_options = {})
|
175
173
|
name = name.to_sym
|
176
174
|
valid_scope_name?(name)
|
@@ -26,7 +26,7 @@ module ActiveRecord
|
|
26
26
|
relation = relation.and(table[finder_class.primary_key.to_sym].not_eq(record.send(:id))) if record.persisted?
|
27
27
|
|
28
28
|
Array.wrap(options[:scope]).each do |scope_item|
|
29
|
-
scope_value = record.
|
29
|
+
scope_value = record.read_attribute(scope_item)
|
30
30
|
relation = relation.and(table[scope_item].eq(scope_value))
|
31
31
|
end
|
32
32
|
|
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: 3.2.
|
4
|
+
version: 3.2.13.rc1
|
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: 2013-02-
|
11
|
+
date: 2013-02-27 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activesupport
|
@@ -16,54 +16,54 @@ dependencies:
|
|
16
16
|
requirements:
|
17
17
|
- - '='
|
18
18
|
- !ruby/object:Gem::Version
|
19
|
-
version: 3.2.
|
19
|
+
version: 3.2.13.rc1
|
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: 3.2.
|
26
|
+
version: 3.2.13.rc1
|
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: 3.2.
|
33
|
+
version: 3.2.13.rc1
|
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: 3.2.
|
40
|
+
version: 3.2.13.rc1
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
42
|
name: arel
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
44
44
|
requirements:
|
45
|
-
- -
|
45
|
+
- - ~>
|
46
46
|
- !ruby/object:Gem::Version
|
47
47
|
version: 3.0.2
|
48
48
|
type: :runtime
|
49
49
|
prerelease: false
|
50
50
|
version_requirements: !ruby/object:Gem::Requirement
|
51
51
|
requirements:
|
52
|
-
- -
|
52
|
+
- - ~>
|
53
53
|
- !ruby/object:Gem::Version
|
54
54
|
version: 3.0.2
|
55
55
|
- !ruby/object:Gem::Dependency
|
56
56
|
name: tzinfo
|
57
57
|
requirement: !ruby/object:Gem::Requirement
|
58
58
|
requirements:
|
59
|
-
- -
|
59
|
+
- - ~>
|
60
60
|
- !ruby/object:Gem::Version
|
61
61
|
version: 0.3.29
|
62
62
|
type: :runtime
|
63
63
|
prerelease: false
|
64
64
|
version_requirements: !ruby/object:Gem::Requirement
|
65
65
|
requirements:
|
66
|
-
- -
|
66
|
+
- - ~>
|
67
67
|
- !ruby/object:Gem::Version
|
68
68
|
version: 0.3.29
|
69
69
|
description: Databases on Rails. Build a persistent domain model by mapping database
|
@@ -229,23 +229,23 @@ licenses: []
|
|
229
229
|
metadata: {}
|
230
230
|
post_install_message:
|
231
231
|
rdoc_options:
|
232
|
-
-
|
232
|
+
- --main
|
233
233
|
- README.rdoc
|
234
234
|
require_paths:
|
235
235
|
- lib
|
236
236
|
required_ruby_version: !ruby/object:Gem::Requirement
|
237
237
|
requirements:
|
238
|
-
- -
|
238
|
+
- - '>='
|
239
239
|
- !ruby/object:Gem::Version
|
240
240
|
version: 1.8.7
|
241
241
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
242
242
|
requirements:
|
243
|
-
- -
|
243
|
+
- - '>'
|
244
244
|
- !ruby/object:Gem::Version
|
245
|
-
version:
|
245
|
+
version: 1.3.1
|
246
246
|
requirements: []
|
247
247
|
rubyforge_project:
|
248
|
-
rubygems_version: 2.0.0
|
248
|
+
rubygems_version: 2.0.0
|
249
249
|
signing_key:
|
250
250
|
specification_version: 4
|
251
251
|
summary: Object-relational mapper framework (part of Rails).
|