activerecord 7.1.1 → 7.1.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/CHANGELOG.md +177 -0
- data/README.rdoc +1 -0
- data/lib/active_record/associations/association.rb +2 -1
- data/lib/active_record/associations/preloader/association.rb +4 -1
- data/lib/active_record/associations.rb +15 -15
- data/lib/active_record/attribute_methods/before_type_cast.rb +1 -1
- data/lib/active_record/attribute_methods/dirty.rb +13 -9
- data/lib/active_record/attribute_methods.rb +1 -1
- data/lib/active_record/callbacks.rb +2 -2
- data/lib/active_record/connection_adapters/abstract/connection_pool.rb +11 -8
- data/lib/active_record/connection_adapters/abstract/database_statements.rb +4 -2
- data/lib/active_record/connection_adapters/abstract/query_cache.rb +2 -1
- data/lib/active_record/connection_adapters/abstract_adapter.rb +13 -4
- data/lib/active_record/connection_adapters/mysql2/database_statements.rb +3 -0
- data/lib/active_record/connection_adapters/postgresql/database_statements.rb +4 -1
- data/lib/active_record/connection_adapters/postgresql/oid/money.rb +3 -2
- data/lib/active_record/connection_adapters/postgresql/schema_statements.rb +12 -5
- data/lib/active_record/connection_adapters/postgresql_adapter.rb +32 -33
- data/lib/active_record/connection_adapters/sqlite3/database_statements.rb +10 -3
- data/lib/active_record/connection_adapters/trilogy/database_statements.rb +1 -0
- data/lib/active_record/connection_adapters/trilogy_adapter.rb +9 -1
- data/lib/active_record/connection_handling.rb +1 -1
- data/lib/active_record/core.rb +41 -7
- data/lib/active_record/delegated_type.rb +1 -1
- data/lib/active_record/encryption/encryptable_record.rb +7 -1
- data/lib/active_record/encryption/encrypted_attribute_type.rb +4 -0
- data/lib/active_record/encryption/extended_deterministic_queries.rb +0 -15
- data/lib/active_record/enum.rb +6 -9
- data/lib/active_record/errors.rb +5 -4
- data/lib/active_record/fixtures.rb +16 -0
- data/lib/active_record/future_result.rb +1 -0
- data/lib/active_record/gem_version.rb +1 -1
- data/lib/active_record/insert_all.rb +3 -3
- data/lib/active_record/internal_metadata.rb +1 -1
- data/lib/active_record/middleware/database_selector.rb +1 -1
- data/lib/active_record/migration/compatibility.rb +8 -0
- data/lib/active_record/migration/pending_migration_connection.rb +21 -0
- data/lib/active_record/migration.rb +9 -5
- data/lib/active_record/model_schema.rb +5 -5
- data/lib/active_record/nested_attributes.rb +3 -3
- data/lib/active_record/normalization.rb +8 -0
- data/lib/active_record/persistence.rb +4 -3
- data/lib/active_record/promise.rb +1 -1
- data/lib/active_record/railties/controller_runtime.rb +2 -1
- data/lib/active_record/railties/databases.rake +5 -5
- data/lib/active_record/reflection.rb +13 -1
- data/lib/active_record/relation/calculations.rb +28 -1
- data/lib/active_record/relation/delegation.rb +1 -1
- data/lib/active_record/relation.rb +18 -3
- data/lib/active_record/runtime_registry.rb +15 -1
- data/lib/active_record/schema_migration.rb +1 -1
- data/lib/active_record/secure_token.rb +1 -1
- data/lib/active_record/tasks/database_tasks.rb +5 -5
- data/lib/arel/nodes/homogeneous_in.rb +1 -1
- metadata +10 -9
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 9f7c51f040979b7650eb209b0dc856a0877bccc968dd99cde06e3cf1776dd638
|
4
|
+
data.tar.gz: b81eca56b185f087c95b6691b307ff1c9c63d0d03ff650b729e943888f053152
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 6f68dc9e6cdccf23f5467810a68083564760601aa3c82b4c85720cfb2c39500439a86bb63c2ce8fea37337de6fc4f157722300c691cfd239e92732569b5c20f6
|
7
|
+
data.tar.gz: 6f8382df74c2c16b873cab0effeda0a3ef3e578d5087e435d7d2f8c6890dcf0d85e2211f2bc890182af49e836b09e4e345e2b9bc37eb8472814e98bb6636b005
|
data/CHANGELOG.md
CHANGED
@@ -1,3 +1,176 @@
|
|
1
|
+
## Rails 7.1.3 (January 16, 2024) ##
|
2
|
+
|
3
|
+
* Fix Migrations with versions older than 7.1 validating options given to
|
4
|
+
`add_reference`.
|
5
|
+
|
6
|
+
*Hartley McGuire*
|
7
|
+
|
8
|
+
* Ensure `reload` sets correct owner for each association.
|
9
|
+
|
10
|
+
*Dmytro Savochkin*
|
11
|
+
|
12
|
+
* Fix view runtime for controllers with async queries.
|
13
|
+
|
14
|
+
*fatkodima*
|
15
|
+
|
16
|
+
* Fix `load_async` to work with query cache.
|
17
|
+
|
18
|
+
*fatkodima*
|
19
|
+
|
20
|
+
* Fix polymorphic `belongs_to` to correctly use parent's `query_constraints`.
|
21
|
+
|
22
|
+
*fatkodima*
|
23
|
+
|
24
|
+
* Fix `Preloader` to not generate a query for already loaded association with `query_constraints`.
|
25
|
+
|
26
|
+
*fatkodima*
|
27
|
+
|
28
|
+
* Fix multi-database polymorphic preloading with equivalent table names.
|
29
|
+
|
30
|
+
When preloading polymorphic associations, if two models pointed to two
|
31
|
+
tables with the same name but located in different databases, the
|
32
|
+
preloader would only load one.
|
33
|
+
|
34
|
+
*Ari Summer*
|
35
|
+
|
36
|
+
* Fix `encrypted_attribute?` to take into account context properties passed to `encrypts`.
|
37
|
+
|
38
|
+
*Maxime Réty*
|
39
|
+
|
40
|
+
* Fix `find_by` to work correctly in presence of composite primary keys.
|
41
|
+
|
42
|
+
*fatkodima*
|
43
|
+
|
44
|
+
* Fix async queries sometimes returning a raw result if they hit the query cache.
|
45
|
+
|
46
|
+
`ShipPart.async_count` could return a raw integer rather than a Promise
|
47
|
+
if it found the result in the query cache.
|
48
|
+
|
49
|
+
*fatkodima*
|
50
|
+
|
51
|
+
* Fix `Relation#transaction` to not apply a default scope.
|
52
|
+
|
53
|
+
The method was incorrectly setting a default scope around its block:
|
54
|
+
|
55
|
+
```ruby
|
56
|
+
Post.where(published: true).transaction do
|
57
|
+
Post.count # SELECT COUNT(*) FROM posts WHERE published = FALSE;
|
58
|
+
end
|
59
|
+
```
|
60
|
+
|
61
|
+
*Jean Boussier*
|
62
|
+
|
63
|
+
* Fix calling `async_pluck` on a `none` relation.
|
64
|
+
|
65
|
+
`Model.none.async_pluck(:id)` was returning a naked value
|
66
|
+
instead of a promise.
|
67
|
+
|
68
|
+
*Jean Boussier*
|
69
|
+
|
70
|
+
* Fix calling `load_async` on a `none` relation.
|
71
|
+
|
72
|
+
`Model.none.load_async` was returning a broken result.
|
73
|
+
|
74
|
+
*Lucas Mazza*
|
75
|
+
|
76
|
+
* TrilogyAdapter: ignore `host` if `socket` parameter is set.
|
77
|
+
|
78
|
+
This allows to configure a connection on a UNIX socket via DATABASE_URL:
|
79
|
+
|
80
|
+
```
|
81
|
+
DATABASE_URL=trilogy://does-not-matter/my_db_production?socket=/var/run/mysql.sock
|
82
|
+
```
|
83
|
+
|
84
|
+
*Jean Boussier*
|
85
|
+
|
86
|
+
* Fix `has_secure_token` calls the setter method on initialize.
|
87
|
+
|
88
|
+
*Abeid Ahmed*
|
89
|
+
|
90
|
+
* Allow using `object_id` as a database column name.
|
91
|
+
It was available before rails 7.1 and may be used as a part of polymorphic relationship to `object` where `object` can be any other database record.
|
92
|
+
|
93
|
+
*Mikhail Doronin*
|
94
|
+
|
95
|
+
* Fix `rails db:create:all` to not touch databases before they are created.
|
96
|
+
|
97
|
+
*fatkodima*
|
98
|
+
|
99
|
+
|
100
|
+
## Rails 7.1.2 (November 10, 2023) ##
|
101
|
+
|
102
|
+
* Fix renaming primary key index when renaming a table with a UUID primary key
|
103
|
+
in PostgreSQL.
|
104
|
+
|
105
|
+
*fatkodima*
|
106
|
+
|
107
|
+
* Fix `where(field: values)` queries when `field` is a serialized attribute
|
108
|
+
(for example, when `field` uses `ActiveRecord::Base.serialize` or is a JSON
|
109
|
+
column).
|
110
|
+
|
111
|
+
*João Alves*
|
112
|
+
|
113
|
+
* Prevent marking broken connections as verified.
|
114
|
+
|
115
|
+
*Daniel Colson*
|
116
|
+
|
117
|
+
* Don't mark Float::INFINITY as changed when reassigning it
|
118
|
+
|
119
|
+
When saving a record with a float infinite value, it shouldn't mark as changed
|
120
|
+
|
121
|
+
*Maicol Bentancor*
|
122
|
+
|
123
|
+
* `ActiveRecord::Base.table_name` now returns `nil` instead of raising
|
124
|
+
"undefined method `abstract_class?` for Object:Class".
|
125
|
+
|
126
|
+
*a5-stable*
|
127
|
+
|
128
|
+
* Fix upserting for custom `:on_duplicate` and `:unique_by` consisting of all
|
129
|
+
inserts keys.
|
130
|
+
|
131
|
+
*fatkodima*
|
132
|
+
|
133
|
+
* Fixed an [issue](https://github.com/rails/rails/issues/49809) where saving a
|
134
|
+
record could innappropriately `dup` its attributes.
|
135
|
+
|
136
|
+
*Jonathan Hefner*
|
137
|
+
|
138
|
+
* Dump schema only for a specific db for rollback/up/down tasks for multiple dbs.
|
139
|
+
|
140
|
+
*fatkodima*
|
141
|
+
|
142
|
+
* Fix `NoMethodError` when casting a PostgreSQL `money` value that uses a
|
143
|
+
comma as its radix point and has no leading currency symbol. For example,
|
144
|
+
when casting `"3,50"`.
|
145
|
+
|
146
|
+
*Andreas Reischuck* and *Jonathan Hefner*
|
147
|
+
|
148
|
+
* Re-enable support for using `enum` with non-column-backed attributes.
|
149
|
+
Non-column-backed attributes must be previously declared with an explicit
|
150
|
+
type. For example:
|
151
|
+
|
152
|
+
```ruby
|
153
|
+
class Post < ActiveRecord::Base
|
154
|
+
attribute :topic, :string
|
155
|
+
enum topic: %i[science tech engineering math]
|
156
|
+
end
|
157
|
+
```
|
158
|
+
|
159
|
+
*Jonathan Hefner*
|
160
|
+
|
161
|
+
* Raise on `foreign_key:` being passed as an array in associations
|
162
|
+
|
163
|
+
*Nikita Vasilevsky*
|
164
|
+
|
165
|
+
* Return back maximum allowed PostgreSQL table name to 63 characters.
|
166
|
+
|
167
|
+
*fatkodima*
|
168
|
+
|
169
|
+
* Fix detecting `IDENTITY` columns for PostgreSQL < 10.
|
170
|
+
|
171
|
+
*fatkodima*
|
172
|
+
|
173
|
+
|
1
174
|
## Rails 7.1.1 (October 11, 2023) ##
|
2
175
|
|
3
176
|
* Fix auto populating IDENTITY columns for PostgreSQL.
|
@@ -165,6 +338,10 @@
|
|
165
338
|
|
166
339
|
*Adam Hess*
|
167
340
|
|
341
|
+
* Deprecate aliasing non-attributes with `alias_attribute`.
|
342
|
+
|
343
|
+
*Ian Candy*
|
344
|
+
|
168
345
|
* Fix unscope is not working in specific case
|
169
346
|
|
170
347
|
Before:
|
data/README.rdoc
CHANGED
@@ -166,6 +166,7 @@ Active Record is an implementation of the object-relational mapping (ORM)
|
|
166
166
|
pattern[https://www.martinfowler.com/eaaCatalog/activeRecord.html] by the same
|
167
167
|
name described by Martin Fowler:
|
168
168
|
|
169
|
+
>>>
|
169
170
|
"An object that wraps a row in a database table or view,
|
170
171
|
encapsulates the database access, and adds domain logic on that data."
|
171
172
|
|
@@ -33,7 +33,8 @@ module ActiveRecord
|
|
33
33
|
# <tt>owner</tt>, the collection of its posts as <tt>target</tt>, and
|
34
34
|
# the <tt>reflection</tt> object represents a <tt>:has_many</tt> macro.
|
35
35
|
class Association # :nodoc:
|
36
|
-
|
36
|
+
attr_accessor :owner
|
37
|
+
attr_reader :target, :reflection, :disable_joins
|
37
38
|
|
38
39
|
delegate :options, to: :reflection
|
39
40
|
|
@@ -17,11 +17,12 @@ module ActiveRecord
|
|
17
17
|
def eql?(other)
|
18
18
|
association_key_name == other.association_key_name &&
|
19
19
|
scope.table_name == other.scope.table_name &&
|
20
|
+
scope.connection_specification_name == other.scope.connection_specification_name &&
|
20
21
|
scope.values_for_queries == other.scope.values_for_queries
|
21
22
|
end
|
22
23
|
|
23
24
|
def hash
|
24
|
-
[association_key_name, scope.table_name, scope.values_for_queries].hash
|
25
|
+
[association_key_name, scope.table_name, scope.connection_specification_name, scope.values_for_queries].hash
|
25
26
|
end
|
26
27
|
|
27
28
|
def records_for(loaders)
|
@@ -38,6 +39,8 @@ module ActiveRecord
|
|
38
39
|
end
|
39
40
|
|
40
41
|
def load_records_for_keys(keys, &block)
|
42
|
+
return [] if keys.empty?
|
43
|
+
|
41
44
|
if association_key_name.is_a?(Array)
|
42
45
|
query_constraints = Hash.new { |hsh, key| hsh[key] = Set.new }
|
43
46
|
|
@@ -1050,7 +1050,7 @@ module ActiveRecord
|
|
1050
1050
|
# query per addressable type.
|
1051
1051
|
# For example, if all the addressables are either of class Person or Company, then a total
|
1052
1052
|
# of 3 queries will be executed. The list of addressable types to load is determined on
|
1053
|
-
# the back of the addresses loaded. This is not supported if Active Record has to
|
1053
|
+
# the back of the addresses loaded. This is not supported if Active Record has to fall back
|
1054
1054
|
# to the previous implementation of eager loading and will raise ActiveRecord::EagerLoadPolymorphicError.
|
1055
1055
|
# The reason is that the parent model's type is a column value so its corresponding table
|
1056
1056
|
# name cannot be put in the +FROM+/+JOIN+ clauses of that query.
|
@@ -1339,7 +1339,7 @@ module ActiveRecord
|
|
1339
1339
|
# Returns a Relation of all of the associated objects, forcing a database read.
|
1340
1340
|
# An empty Relation is returned if none are found.
|
1341
1341
|
#
|
1342
|
-
#
|
1342
|
+
# ==== Example
|
1343
1343
|
#
|
1344
1344
|
# class Firm < ActiveRecord::Base
|
1345
1345
|
# has_many :clients
|
@@ -1369,7 +1369,7 @@ module ActiveRecord
|
|
1369
1369
|
#
|
1370
1370
|
# The declaration can also include an +options+ hash to specialize the behavior of the association.
|
1371
1371
|
#
|
1372
|
-
#
|
1372
|
+
# ==== Scopes
|
1373
1373
|
#
|
1374
1374
|
# You can pass a second argument +scope+ as a callable (i.e. proc or
|
1375
1375
|
# lambda) to retrieve a specific set of records or customize the generated
|
@@ -1380,7 +1380,7 @@ module ActiveRecord
|
|
1380
1380
|
# has_many :employees, -> { joins(:address) }
|
1381
1381
|
# has_many :posts, ->(blog) { where("max_post_length > ?", blog.max_post_length) }
|
1382
1382
|
#
|
1383
|
-
#
|
1383
|
+
# ==== Extensions
|
1384
1384
|
#
|
1385
1385
|
# The +extension+ argument allows you to pass a block into a has_many
|
1386
1386
|
# association. This is useful for adding new finders, creators, and other
|
@@ -1394,7 +1394,7 @@ module ActiveRecord
|
|
1394
1394
|
# end
|
1395
1395
|
# end
|
1396
1396
|
#
|
1397
|
-
#
|
1397
|
+
# ==== Options
|
1398
1398
|
# [+:class_name+]
|
1399
1399
|
# Specify the class name of the association. Use it only if that name can't be inferred
|
1400
1400
|
# from the association name. So <tt>has_many :products</tt> will by default be linked
|
@@ -1556,7 +1556,7 @@ module ActiveRecord
|
|
1556
1556
|
# [<tt>reset_association</tt>]
|
1557
1557
|
# Unloads the associated object. The next access will query it from the database.
|
1558
1558
|
#
|
1559
|
-
#
|
1559
|
+
# ==== Example
|
1560
1560
|
#
|
1561
1561
|
# class Account < ActiveRecord::Base
|
1562
1562
|
# has_one :beneficiary
|
@@ -1575,7 +1575,7 @@ module ActiveRecord
|
|
1575
1575
|
# account.reload_beneficiary
|
1576
1576
|
# account.reset_beneficiary
|
1577
1577
|
#
|
1578
|
-
#
|
1578
|
+
# ==== Scopes
|
1579
1579
|
#
|
1580
1580
|
# You can pass a second argument +scope+ as a callable (i.e. proc or
|
1581
1581
|
# lambda) to retrieve a specific record or customize the generated query
|
@@ -1586,7 +1586,7 @@ module ActiveRecord
|
|
1586
1586
|
# has_one :employer, -> { joins(:company) }
|
1587
1587
|
# has_one :latest_post, ->(blog) { where("created_at > ?", blog.enabled_at) }
|
1588
1588
|
#
|
1589
|
-
#
|
1589
|
+
# ==== Options
|
1590
1590
|
#
|
1591
1591
|
# The declaration can also include an +options+ hash to specialize the behavior of the association.
|
1592
1592
|
#
|
@@ -1745,7 +1745,7 @@ module ActiveRecord
|
|
1745
1745
|
# [<tt>association_previously_changed?</tt>]
|
1746
1746
|
# Returns true if the previous save updated the association to reference a new associate object.
|
1747
1747
|
#
|
1748
|
-
#
|
1748
|
+
# ==== Example
|
1749
1749
|
#
|
1750
1750
|
# class Post < ActiveRecord::Base
|
1751
1751
|
# belongs_to :author
|
@@ -1766,7 +1766,7 @@ module ActiveRecord
|
|
1766
1766
|
# post.author_changed?
|
1767
1767
|
# post.author_previously_changed?
|
1768
1768
|
#
|
1769
|
-
#
|
1769
|
+
# ==== Scopes
|
1770
1770
|
#
|
1771
1771
|
# You can pass a second argument +scope+ as a callable (i.e. proc or
|
1772
1772
|
# lambda) to retrieve a specific record or customize the generated query
|
@@ -1777,7 +1777,7 @@ module ActiveRecord
|
|
1777
1777
|
# belongs_to :user, -> { joins(:friends) }
|
1778
1778
|
# belongs_to :level, ->(game) { where("game_level > ?", game.current_level) }
|
1779
1779
|
#
|
1780
|
-
#
|
1780
|
+
# ==== Options
|
1781
1781
|
#
|
1782
1782
|
# The declaration can also include an +options+ hash to specialize the behavior of the association.
|
1783
1783
|
#
|
@@ -1964,7 +1964,7 @@ module ActiveRecord
|
|
1964
1964
|
# Returns a Relation of all of the associated objects, forcing a database read.
|
1965
1965
|
# An empty Relation is returned if none are found.
|
1966
1966
|
#
|
1967
|
-
#
|
1967
|
+
# ==== Example
|
1968
1968
|
#
|
1969
1969
|
# class Developer < ActiveRecord::Base
|
1970
1970
|
# has_and_belongs_to_many :projects
|
@@ -1993,7 +1993,7 @@ module ActiveRecord
|
|
1993
1993
|
#
|
1994
1994
|
# The declaration may include an +options+ hash to specialize the behavior of the association.
|
1995
1995
|
#
|
1996
|
-
#
|
1996
|
+
# ==== Scopes
|
1997
1997
|
#
|
1998
1998
|
# You can pass a second argument +scope+ as a callable (i.e. proc or
|
1999
1999
|
# lambda) to retrieve a specific set of records or customize the generated
|
@@ -2005,7 +2005,7 @@ module ActiveRecord
|
|
2005
2005
|
# where("default_category = ?", post.default_category)
|
2006
2006
|
# }
|
2007
2007
|
#
|
2008
|
-
#
|
2008
|
+
# ==== Extensions
|
2009
2009
|
#
|
2010
2010
|
# The +extension+ argument allows you to pass a block into a
|
2011
2011
|
# has_and_belongs_to_many association. This is useful for adding new
|
@@ -2020,7 +2020,7 @@ module ActiveRecord
|
|
2020
2020
|
# end
|
2021
2021
|
# end
|
2022
2022
|
#
|
2023
|
-
#
|
2023
|
+
# ==== Options
|
2024
2024
|
#
|
2025
2025
|
# [+:class_name+]
|
2026
2026
|
# Specify the class name of the association. Use it only if that name can't be inferred
|
@@ -14,7 +14,7 @@ module ActiveRecord
|
|
14
14
|
# class Person < ActiveRecord::Base
|
15
15
|
# end
|
16
16
|
#
|
17
|
-
# person = Person.create(name: "
|
17
|
+
# person = Person.create(name: "Allison")
|
18
18
|
# person.changed? # => false
|
19
19
|
#
|
20
20
|
# Change the name:
|
@@ -76,11 +76,13 @@ module ActiveRecord
|
|
76
76
|
#
|
77
77
|
# ==== Options
|
78
78
|
#
|
79
|
-
# +from+
|
80
|
-
#
|
79
|
+
# [+from+]
|
80
|
+
# When specified, this method will return false unless the original
|
81
|
+
# value is equal to the given value.
|
81
82
|
#
|
82
|
-
# +to+
|
83
|
-
#
|
83
|
+
# [+to+]
|
84
|
+
# When specified, this method will return false unless the value will be
|
85
|
+
# changed to the given value.
|
84
86
|
def saved_change_to_attribute?(attr_name, **options)
|
85
87
|
mutations_before_last_save.changed?(attr_name.to_s, **options)
|
86
88
|
end
|
@@ -126,11 +128,13 @@ module ActiveRecord
|
|
126
128
|
#
|
127
129
|
# ==== Options
|
128
130
|
#
|
129
|
-
# +from+
|
130
|
-
#
|
131
|
+
# [+from+]
|
132
|
+
# When specified, this method will return false unless the original
|
133
|
+
# value is equal to the given value.
|
131
134
|
#
|
132
|
-
# +to+
|
133
|
-
#
|
135
|
+
# [+to+]
|
136
|
+
# When specified, this method will return false unless the value will be
|
137
|
+
# changed to the given value.
|
134
138
|
def will_save_change_to_attribute?(attr_name, **options)
|
135
139
|
mutations_from_database.changed?(attr_name.to_s, **options)
|
136
140
|
end
|
@@ -34,7 +34,7 @@ module ActiveRecord
|
|
34
34
|
Base.private_instance_methods -
|
35
35
|
Base.superclass.instance_methods -
|
36
36
|
Base.superclass.private_instance_methods +
|
37
|
-
%i[__id__ dup freeze frozen? hash
|
37
|
+
%i[__id__ dup freeze frozen? hash class clone]
|
38
38
|
).map { |m| -m.to_s }.to_set.freeze
|
39
39
|
end
|
40
40
|
end
|
@@ -241,8 +241,8 @@ module ActiveRecord
|
|
241
241
|
#
|
242
242
|
# config.active_record.run_after_transaction_callbacks_in_order_defined = false
|
243
243
|
#
|
244
|
-
#
|
245
|
-
# are defined, just like the example above.
|
244
|
+
# When set to +true+ (the default from \Rails 7.1), callbacks are executed in the order they
|
245
|
+
# are defined, just like the example above. When set to +false+, the order is reversed, so
|
246
246
|
# +do_something_else+ is executed before +log_children+.
|
247
247
|
#
|
248
248
|
# == \Transactions
|
@@ -58,12 +58,10 @@ module ActiveRecord
|
|
58
58
|
# Connections can be obtained and used from a connection pool in several
|
59
59
|
# ways:
|
60
60
|
#
|
61
|
-
# 1. Simply use {ActiveRecord::Base.connection}[rdoc-ref:ConnectionHandling.connection]
|
62
|
-
#
|
63
|
-
# earlier (pre-connection-pooling). Eventually, when you're done with
|
64
|
-
# the connection(s) and wish it to be returned to the pool, you call
|
61
|
+
# 1. Simply use {ActiveRecord::Base.connection}[rdoc-ref:ConnectionHandling.connection].
|
62
|
+
# When you're done with the connection(s) and wish it to be returned to the pool, you call
|
65
63
|
# {ActiveRecord::Base.connection_handler.clear_active_connections!}[rdoc-ref:ConnectionAdapters::ConnectionHandler#clear_active_connections!].
|
66
|
-
# This
|
64
|
+
# This is the default behavior for Active Record when used in conjunction with
|
67
65
|
# Action Pack's request handling cycle.
|
68
66
|
# 2. Manually check out a connection from the pool with
|
69
67
|
# {ActiveRecord::Base.connection_pool.checkout}[rdoc-ref:#checkout]. You are responsible for
|
@@ -465,8 +463,7 @@ module ActiveRecord
|
|
465
463
|
@available.num_waiting
|
466
464
|
end
|
467
465
|
|
468
|
-
#
|
469
|
-
# Example:
|
466
|
+
# Returns the connection pool's usage statistic.
|
470
467
|
#
|
471
468
|
# ActiveRecord::Base.connection_pool.stat # => { size: 15, connections: 1, busy: 1, dead: 0, idle: 0, waiting: 0, checkout_timeout: 5 }
|
472
469
|
def stat
|
@@ -658,7 +655,13 @@ module ActiveRecord
|
|
658
655
|
conn
|
659
656
|
else
|
660
657
|
reap
|
661
|
-
|
658
|
+
# Retry after reaping, which may return an available connection,
|
659
|
+
# remove an inactive connection, or both
|
660
|
+
if conn = @available.poll || try_to_checkout_new_connection
|
661
|
+
conn
|
662
|
+
else
|
663
|
+
@available.poll(checkout_timeout)
|
664
|
+
end
|
662
665
|
end
|
663
666
|
end
|
664
667
|
|
@@ -189,8 +189,10 @@ module ActiveRecord
|
|
189
189
|
def insert(arel, name = nil, pk = nil, id_value = nil, sequence_name = nil, binds = [], returning: nil)
|
190
190
|
sql, binds = to_sql_and_binds(arel, binds)
|
191
191
|
value = exec_insert(sql, name, binds, pk, sequence_name, returning: returning)
|
192
|
-
|
193
|
-
|
192
|
+
|
193
|
+
return returning_column_values(value) unless returning.nil?
|
194
|
+
|
195
|
+
id_value || last_inserted_id(value)
|
194
196
|
end
|
195
197
|
alias create insert
|
196
198
|
|
@@ -106,7 +106,8 @@ module ActiveRecord
|
|
106
106
|
sql, binds, preparable = to_sql_and_binds(arel, binds, preparable)
|
107
107
|
|
108
108
|
if async
|
109
|
-
lookup_sql_cache(sql, name, binds) || super(sql, name, binds, preparable: preparable, async: async)
|
109
|
+
result = lookup_sql_cache(sql, name, binds) || super(sql, name, binds, preparable: preparable, async: async)
|
110
|
+
FutureResult::Complete.new(result)
|
110
111
|
else
|
111
112
|
cache_sql(sql, name, binds) { super(sql, name, binds, preparable: preparable, async: async) }
|
112
113
|
end
|
@@ -970,7 +970,11 @@ module ActiveRecord
|
|
970
970
|
# If +allow_retry+ is true, a connection-related exception will
|
971
971
|
# cause an automatic reconnect and re-run of the block, up to
|
972
972
|
# the connection's configured +connection_retries+ setting
|
973
|
-
# and the configured +retry_deadline+ limit.
|
973
|
+
# and the configured +retry_deadline+ limit. (Note that when
|
974
|
+
# +allow_retry+ is true, it's possible to return without having marked
|
975
|
+
# the connection as verified. If the block is guaranteed to exercise the
|
976
|
+
# connection, consider calling `verified!` to avoid needless
|
977
|
+
# verification queries in subsequent calls.)
|
974
978
|
#
|
975
979
|
# If +materialize_transactions+ is false, the block will be run without
|
976
980
|
# ensuring virtual transactions have been materialized in the DB
|
@@ -1021,9 +1025,7 @@ module ActiveRecord
|
|
1021
1025
|
end
|
1022
1026
|
|
1023
1027
|
begin
|
1024
|
-
|
1025
|
-
@verified = true
|
1026
|
-
result
|
1028
|
+
yield @raw_connection
|
1027
1029
|
rescue => original_exception
|
1028
1030
|
translated_exception = translate_exception_class(original_exception, nil, nil)
|
1029
1031
|
invalidate_transaction(translated_exception)
|
@@ -1058,6 +1060,13 @@ module ActiveRecord
|
|
1058
1060
|
end
|
1059
1061
|
end
|
1060
1062
|
|
1063
|
+
# Mark the connection as verified. Call this inside a
|
1064
|
+
# `with_raw_connection` block only when the block is guaranteed to
|
1065
|
+
# exercise the raw connection.
|
1066
|
+
def verified!
|
1067
|
+
@verified = true
|
1068
|
+
end
|
1069
|
+
|
1061
1070
|
def retryable_connection_error?(exception)
|
1062
1071
|
exception.is_a?(ConnectionNotEstablished) || exception.is_a?(ConnectionFailed)
|
1063
1072
|
end
|
@@ -98,6 +98,7 @@ module ActiveRecord
|
|
98
98
|
with_raw_connection(allow_retry: allow_retry, materialize_transactions: materialize_transactions) do |conn|
|
99
99
|
sync_timezone_changes(conn)
|
100
100
|
result = conn.query(sql)
|
101
|
+
verified!
|
101
102
|
handle_warnings(sql)
|
102
103
|
result
|
103
104
|
end
|
@@ -126,6 +127,8 @@ module ActiveRecord
|
|
126
127
|
result = ActiveSupport::Dependencies.interlock.permit_concurrent_loads do
|
127
128
|
stmt.execute(*type_casted_binds)
|
128
129
|
end
|
130
|
+
verified!
|
131
|
+
result
|
129
132
|
rescue ::Mysql2::Error => e
|
130
133
|
if cache_stmt
|
131
134
|
@statements.delete(sql)
|
@@ -16,7 +16,9 @@ module ActiveRecord
|
|
16
16
|
|
17
17
|
log(sql, name) do
|
18
18
|
with_raw_connection do |conn|
|
19
|
-
conn.async_exec(sql).map_types!(@type_map_for_results).values
|
19
|
+
result = conn.async_exec(sql).map_types!(@type_map_for_results).values
|
20
|
+
verified!
|
21
|
+
result
|
20
22
|
end
|
21
23
|
end
|
22
24
|
end
|
@@ -51,6 +53,7 @@ module ActiveRecord
|
|
51
53
|
log(sql, name, async: async) do
|
52
54
|
with_raw_connection(allow_retry: allow_retry, materialize_transactions: materialize_transactions) do |conn|
|
53
55
|
result = conn.async_exec(sql)
|
56
|
+
verified!
|
54
57
|
handle_warnings(result)
|
55
58
|
result
|
56
59
|
end
|
@@ -27,9 +27,10 @@ module ActiveRecord
|
|
27
27
|
value = value.sub(/^\((.+)\)$/, '-\1') # (4)
|
28
28
|
case value
|
29
29
|
when /^-?\D*+[\d,]+\.\d{2}$/ # (1)
|
30
|
-
value.
|
30
|
+
value.delete!("^-0-9.")
|
31
31
|
when /^-?\D*+[\d.]+,\d{2}$/ # (2)
|
32
|
-
value.
|
32
|
+
value.delete!("^-0-9,")
|
33
|
+
value.tr!(",", ".")
|
33
34
|
end
|
34
35
|
|
35
36
|
super(value)
|
@@ -341,7 +341,7 @@ module ActiveRecord
|
|
341
341
|
JOIN pg_namespace nsp ON (t.relnamespace = nsp.oid)
|
342
342
|
WHERE t.oid = #{quote(quote_table_name(table))}::regclass
|
343
343
|
AND cons.contype = 'p'
|
344
|
-
AND pg_get_expr(def.adbin, def.adrelid) ~* 'nextval|uuid_generate'
|
344
|
+
AND pg_get_expr(def.adbin, def.adrelid) ~* 'nextval|uuid_generate|gen_random_uuid'
|
345
345
|
SQL
|
346
346
|
end
|
347
347
|
|
@@ -385,11 +385,18 @@ module ActiveRecord
|
|
385
385
|
execute "ALTER TABLE #{quote_table_name(table_name)} RENAME TO #{quote_table_name(new_name)}"
|
386
386
|
pk, seq = pk_and_sequence_for(new_name)
|
387
387
|
if pk
|
388
|
-
|
389
|
-
|
388
|
+
# PostgreSQL automatically creates an index for PRIMARY KEY with name consisting of
|
389
|
+
# truncated table name and "_pkey" suffix fitting into max_identifier_length number of characters.
|
390
|
+
max_pkey_prefix = max_identifier_length - "_pkey".size
|
391
|
+
idx = "#{table_name[0, max_pkey_prefix]}_pkey"
|
392
|
+
new_idx = "#{new_name[0, max_pkey_prefix]}_pkey"
|
390
393
|
execute "ALTER INDEX #{quote_table_name(idx)} RENAME TO #{quote_table_name(new_idx)}"
|
391
|
-
|
392
|
-
|
394
|
+
|
395
|
+
# PostgreSQL automatically creates a sequence for PRIMARY KEY with name consisting of
|
396
|
+
# truncated table name and "#{primary_key}_seq" suffix fitting into max_identifier_length number of characters.
|
397
|
+
max_seq_prefix = max_identifier_length - "_#{pk}_seq".size
|
398
|
+
if seq && seq.identifier == "#{table_name[0, max_seq_prefix]}_#{pk}_seq"
|
399
|
+
new_seq = "#{new_name[0, max_seq_prefix]}_#{pk}_seq"
|
393
400
|
execute "ALTER TABLE #{seq.quoted} RENAME TO #{quote_table_name(new_seq)}"
|
394
401
|
end
|
395
402
|
end
|