| Commit message (Collapse) | Author | Age | Files | Lines |
... | |
| | |
| | |
| | |
| | |
| | | |
`split(/\s*,\s*/)` to order args and then `permit.match?` one by one is
much slower than `permit.match?` once.
|
| | |
| | |
| | |
| | | |
Method added in https://github.com/rails/rails/pull/36416
|
| | |
| | |
| | |
| | |
| | |
| | | |
6c82b6c99d86f37e61f935fb342cccd725d6c7d4
There is no need to be wrapped by `Arel.sql()`.
|
|\ \ \
| | | |
| | | | |
Fix preloading on AR::Relation where records are duplicated by a join
|
| | | | |
|
|\ \ \ \
| | | | |
| | | | | |
Bump rubocop to 0.71
|
| | | | | |
|
|\ \ \ \ \
| |/ / / /
|/| | | | |
Allow quoted identifier string as safe SQL string
|
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | | |
Currently `posts.title` is regarded as a safe SQL string, but
`"posts"."title"` (it is a result of `quote_table_name("posts.title")`)
is regarded as an unsafe SQL string even though a result of
`quote_table_name` should obviously be regarded as a safe SQL string,
since the column name matcher doesn't respect quotation, it is a little
annoying.
This changes the column name matcher to allow quoted identifiers as safe
SQL string, now all results of the `quote_table_name` are regarded as
safe SQL string.
|
|/ / / /
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | | |
This PR proposes moving the schema cache from the connection to the pool
so the connection can ask the pool for the cache. In a future PR our
goal is to be able to read the yaml file from the pool so we can get
rid of the `active_record.check_schema_cache_dump` initializer. This
will fix the issues surrounding dumping the schema cache and mulitple
databases.
Why do we want to get rid of the initializer you ask?
Well I was looking at #34449 and trying to make it work for our usecase
and it revealed A LOT of problems. There are a few issues that I will
fix in remaining PRs with SchemaMigration, but there's a big glaring
issue with this initializer.
When you have an application with multiple databases we'll need to loop
through all the configurations and set the schema cache on those
connections. The problem is on initialization we only have one
connection - the one for Ar::Base. This is fine in a single db
application but not fine in multi-db. If we follow the pattern in #34449
and establish a connection to those other dbs we will end up setting the
cache on the _connection object_ rather than on all connections that
connect for that config.
So even though we looped through the configs and assigned the cache the
cache will not be set (or will be set wrong) once the app is booted
because the connection objects after boot are _different_ than the
connection objects we assigned the cache to.
After trying many different ways to set the schema cache `@tenderlove`
and I came to the conclusion that the initializer is problematic, as is
setting the schema cache twice.
This is part 1 to move the cache to the pool so the cache can read from
the schema cache yaml file instead of setting it when initializing the
app.
To do this we have created a `NullPool` that initializes an empty cache. I
put the `get_schema_cache` and `set_schema_cache` in an `AbstractPool`
so we can share code between `ConnectionPool` and `NullPool` instead of
duplicating code.
Now we only need to set the schema_cache on the pool rather than the
connection. In `discard!` we need to unset the connection from the
schema_cache - we still want the cache just not the connection.
|
|\ \ \ \
| | | | |
| | | | | |
Fixed db:prepare task for multiple databases.
|
| | | | |
| | | | |
| | | | |
| | | | |
| | | | | |
When one database existed already, but not the other,
during setup of missing one, existing database was wiped out.
|
|\ \ \ \ \
| |/ / / /
|/| | | | |
Treat ActiveRecord::Base and ApplicationRecord as "primary"
|
| |/ / /
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | | |
When someone has a multi-db application their `ApplicationRecord` will
look like:
```ruby
class ApplicationRecord < ActiveRecord::Base
self.abstract_class = true
connects_to database: { writing: :primary, reading: :replica }
end
```
This will cause us to open 2 connections to ActiveRecord::Base's
database when we actually only want 1. This is because Rails sees
`ApplicationRecord` and thinks it's a new connection, not the existing
`ActiveRecord::Base` connection because the
`connection_specification_name` is different.
This PR changes `ApplicationRecord` classes to consider themselves the
same as the "primary" connection.
Fixes #36382
|
| | | |
| | | |
| | | |
| | | |
| | | | |
Especially, somehow `CHANGELOG.md` in actiontext and activestorage in
master branch had used 3 spaces indentation.
|
|/ / /
| | |
| | |
| | |
| | |
| | | |
If an sqlite3 table contains a decimal column behind columns with a collation
definition, then parsing the collation of all preceeding columns will fail --
the collation will be missed without notice.
|
|\ \ \
| |/ /
|/| |
| | |
| | | |
guigs/fix-invalid-schema-when-pk-column-has-comment
Fix invalid schema dump when primary key column has a comment
|
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | | |
Before this fix it would either generate an invalid schema, passing `comment` option twice to `create_table`, or it move the comment from primary key column to the table if table had no comment when the dump was generated.
The situation now is that a comment on primary key will be ignored (not present on schema).
Fixes #29966
|
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | | |
`create_table` and `t.column` have the same named options (e.g.
`:comment`, `:primary_key`), so it should be separated table options
from column options.
Related #36373.
|
|\ \ \
| | | |
| | | | |
Avoid making extra 5 arrays in each `save`
|
| |/ /
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | | |
Each `save` calls `all_timestamp_attributes_in_model` to fill timestamp
columns. Allthough the `all_timestamp_attributes_in_model` returns the
same value every time, the `all_timestamp_attributes_in_model` makes
extra 5 arrays every time.
This avoids the making extra 5 arrays by memoizing the result, it makes
`save` economical and a bit faster.
https://gist.github.com/kamipo/1ddad2235073f508637bf9a72d64bb83
Before (2a015f6c0be0593a624b0c800e5335319ac4c660):
```
{["~/rails/activerecord/lib/active_record/timestamp.rb",
76,
:T_ARRAY]=>[1000, 0, 341, 0, 1, 13640],
["~/rails/activerecord/lib/active_record/timestamp.rb",
64,
:T_ARRAY]=>[1000, 0, 341, 0, 1, 13640],
["~/rails/activerecord/lib/active_record/timestamp.rb",
80,
:T_ARRAY]=>[1000, 0, 341, 0, 1, 13640],
["~/rails/activerecord/lib/active_record/timestamp.rb",
68,
:T_ARRAY]=>[1000, 0, 341, 0, 1, 13640],
["~/rails/activerecord/lib/active_record/timestamp.rb",
73,
:T_ARRAY]=>[1000, 0, 341, 0, 1, 13640]}
Warming up --------------------------------------
User.create * 10 36.000 i/100ms
Calculating -------------------------------------
User.create * 10 353.644 (± 7.4%) i/s - 1.764k in 5.021876s
```
After (this change):
```
{["~/rails/activerecord/lib/active_record/timestamp.rb",
83,
:T_ARRAY]=>[1, 0, 1, 1, 1, 40],
["~/rails/activerecord/lib/active_record/timestamp.rb",
87,
:T_ARRAY]=>[1, 0, 1, 1, 1, 40],
["~/rails/activerecord/lib/active_record/timestamp.rb",
64,
:T_ARRAY]=>[1, 1, 1, 1, 1, 0],
["~/rails/activerecord/lib/active_record/timestamp.rb",
69,
:T_ARRAY]=>[1, 1, 1, 1, 1, 0],
["~/rails/activerecord/lib/active_record/timestamp.rb",
74,
:T_ARRAY]=>[1, 1, 1, 1, 1, 0]}
Warming up --------------------------------------
User.create * 10 37.000 i/100ms
Calculating -------------------------------------
User.create * 10 380.063 (± 7.1%) i/s - 1.924k in 5.097917s
```
|
|/ /
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| | |
sort order
```ruby
$ bundle exec rake test_postgresql
... snip ...
Failure:
CalculationsTest#test_pluck_columns_with_same_name [/home/yahonda/git/rails/activerecord/test/cases/calculations_test.rb:842]:
--- expected
+++ actual
@@ -1 +1 @@
-[["The First Topic", "The Second Topic of the day"], ["The Third Topic of the day", "The Fourth Topic of the day"]]
+[["The Third Topic of the day", "The Fourth Topic of the day"], ["The First Topic", "The Second Topic of the day"]]
```
|
| | |
|
| |
| |
| |
| | |
https://buildkite.com/rails/rails/builds/61384#ad441461-87d8-4bdc-a71f-61921fe2df2e/993-1004
|
| |
| |
| |
| |
| | |
`cache_version`
`ActiveRecord::Base.cache_versioning` it `true` by default since Rails 5.2 as stated correctly in the documentation for the `ActiveRecord::Base.cache_versioning` class attribute. Remove the wrong and duplicated documentation of the default value for `cache_versioning` from `cache_version`.
|
| |
| |
| |
| | |
https://buildkite.com/rails/rails/builds/61362#99165d42-172d-4ad5-bf72-b29d8cd44f3e/995-1006
|
|\ \
| | |
| | |
| | |
| | | |
Fix comment for "broken" inverse_of associations
[ci skip]
|
| | | |
|
| | |
| | |
| | |
| | | |
https://buildkite.com/rails/rails/builds/61358#a78ee50e-30b5-48a2-858f-63eba287d919/1290-1298
|
| | | |
|
|\ \ \
| | | |
| | | | |
Allow symbol (i.e. quoted identifier) as safe SQL string
|
| |/ /
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | | |
`pluck(:id)` / `order(:id)` are very common use case, and passed symbol
(i.e. quoted identifier) is obviously safe argument, but
`:id.to_s.split(/\s*,\s*/).all? { |part| permit.match?(part) }` is
useless and a bit expensive operation for each such safe symbols (will
make extra 2 mutable strings, 1 array, 1 proc).
This avoids the expensive operation to such safe symbols, it makes
`pluck(:id)` / `order(:id)` itself about 9% faster.
https://gist.github.com/kamipo/11d428b57f3629a72ae89c6f21721326
Before (93e640735e9363672b770b8d1c5a35f9e464f806):
```
Warming up --------------------------------------
users.pluck(:id) 1.217k i/100ms
users.order(:id).to_sql 1.848k i/100ms
Calculating -------------------------------------
users.pluck(:id) 12.239k (± 8.2%) i/s - 60.850k in 5.013839s
users.order(:id).to_sql 19.111k (± 7.5%) i/s - 96.096k in 5.064450s
```
After (this change):
```
Warming up --------------------------------------
users.pluck(:id) 1.293k i/100ms
users.order(:id).to_sql 2.036k i/100ms
Calculating -------------------------------------
users.pluck(:id) 13.257k (± 6.9%) i/s - 65.943k in 5.002568s
users.order(:id).to_sql 20.957k (± 7.6%) i/s - 105.872k in 5.086102s
```
|
|/ /
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| | |
Prior to 3e2e8eeb9ea552bd4782538cf9348455f3d0e14a the Reaper thread
would hold a reference to connection pools indefinitely, preventing the
connection pool from being garbage collected, and also leaking the
Thread.
Since 3e2e8eeb9ea552bd4782538cf9348455f3d0e14a, there is only one Reaper
Thread for all pools, however all pools are still stored in a class
variable, preventing them from being garbage collected.
This commit instead holds reference to the pools through a WeakRef. This
way, connection pools referenced elsewhere will be reaped, any others
will be able to be garbage collected.
I don't love resorting to WeakRef to solve this, but I believe it's the
simplest way to accomplish the the desired behaviour.
|
| | |
|
|\ \
| | |
| | | |
[CI skip] Put :nodoc: on method that raises NoMethodError
|
| | |
| | |
| | |
| | |
| | | |
This method is not intended to be used so I think we should
remove it from the docs.
|
| | |
| | |
| | |
| | | |
And no longer need to except SCHEMA SQLs manually since 0810c07.
|
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | | |
This reverts commit a1ee4a9ff9d4a3cb255365310ead0dc7b739c6be.
Even if a1ee4a9 is applied, CI is still flakiness.
https://buildkite.com/rails/rails/builds/61252#2c090afa-aa84-4a2b-8b81-9f09219222c6/994-1005
https://buildkite.com/rails/rails/builds/61252#2e55bf83-1bde-44a2-a4f1-b5c3f6820fb4/929-938
Failing tests by whether schema cache is filled or not, it actually
means that whether SCHEMA SQLs are executed or not is not target for the
tests.
So I've reverted commit a1ee4a9 which filling schema cache before
`assert_no_queries`, and replace `assert_no_queries` to
`assert_queries(0)`.
|
| | |
| | |
| | |
| | |
| | | |
Almost all database statements methods except `explain` was moved into
`DatabaseStatements` at #35922. This moves the last one method.
|
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | | |
Unfortunately, a11a8ff had no effect as long as using bind param, and
was not tested.
This ensures making the intent of a11a8ff, which fall back to type
casting from the connection adapter.
Fixes #35205.
```
% ARCONN=postgresql bundle exec ruby -w -Itest test/cases/relation/where_test.rb -n test_type_casting_nested_joins
Using postgresql
Run options: -n test_type_casting_nested_joins --seed 55730
# Running:
E
Error:
ActiveRecord::WhereTest#test_type_casting_nested_joins:
ActiveRecord::StatementInvalid: PG::InvalidTextRepresentation: ERROR: invalid input syntax for integer: "2-foo"
rails test test/cases/relation/where_test.rb:30
Finished in 0.245778s, 4.0687 runs/s, 0.0000 assertions/s.
1 runs, 0 assertions, 0 failures, 1 errors, 0 skips
```
|
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | | |
Testing the result of `capture_sql` is fragile, it is due to whether
SCHEMA SQLs are executed or not depends on whether schema cache is
filled or not.
https://buildkite.com/rails/rails/builds/61248#a5b9dc59-ff0c-40c0-b56e-0895662fbc4c/993-1004
https://buildkite.com/rails/rails/builds/61248#1157b389-f2c7-4554-b6e5-a37624a0e74a/996-1005
I've confirmed all `capture_sql` use cases in our code base, all cases
won't expect SCHEMA SQLs are included.
```
% git grep -n capture_sql
test/cases/associations/belongs_to_associations_test.rb:202: sql = capture_sql { comment.post }
test/cases/associations/belongs_to_associations_test.rb:204: assert_not_equal sql, capture_sql { comment.post }
test/cases/associations/has_many_associations_test.rb:169: sql = capture_sql { post.comments.to_a }
test/cases/associations/has_many_associations_test.rb:171: assert_not_equal sql, capture_sql { post.comments.to_a }
test/cases/associations/has_many_associations_test.rb:276: expected_sql = capture_sql { author.thinking_posts.delete_all }
test/cases/associations/has_many_associations_test.rb:281: loaded_sql = capture_sql { author.thinking_posts.delete_all }
test/cases/associations/has_many_associations_test.rb:289: expected_sql = capture_sql { author.posts.delete_all }
test/cases/associations/has_many_associations_test.rb:294: loaded_sql = capture_sql { author.posts.delete_all }
test/cases/associations/left_outer_join_association_test.rb:22: queries = capture_sql do
test/cases/associations/left_outer_join_association_test.rb:49: queries = capture_sql { Author.left_outer_joins(:posts).to_a }
test/cases/associations/left_outer_join_association_test.rb:54: queries = capture_sql { Author.joins(:posts).left_outer_joins(:posts).to_a }
test/cases/associations/left_outer_join_association_test.rb:60: queries = capture_sql { Author.left_outer_joins({}).to_a }
test/cases/associations/left_outer_join_association_test.rb:65: queries = capture_sql { Author.left_outer_joins([]).to_a }
test/cases/associations/left_outer_join_association_test.rb:78: queries = capture_sql { Author.left_outer_joins(:essays).to_a }
test/cases/associations_test.rb:384: log = capture_sql do
test/cases/associations_test.rb:399: log = capture_sql do
test/cases/associations_test.rb:414: log = capture_sql do
test/cases/associations_test.rb:429: log = capture_sql do
test/cases/associations_test.rb:444: log = capture_sql do
test/cases/associations_test.rb:459: log = capture_sql do
test/cases/reflection_test.rb:307: expected_sql = capture_sql { hotel.recipes.to_a }
test/cases/reflection_test.rb:312: loaded_sql = capture_sql { hotel.recipes.to_a }
test/cases/relation_test.rb:212: queries = capture_sql { Author.joins(:posts).merge(Post.joins(:comments)).to_a }
test/cases/relation_test.rb:232: queries = capture_sql { Post.joins(:author, :categorizations).merge(Author.select(:id)).merge(categorizations_with_authors).to_a }
test/cases/relation_test.rb:347: log = capture_sql do
test/cases/scoping/relation_scoping_test.rb:146: log = capture_sql do
test/cases/scoping/relation_scoping_test.rb:159: log = capture_sql do
test/cases/test_case.rb:33: def capture_sql
test/cases/test_case.rb:41: capture_sql { yield }
```
|
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | |
| | | |
#36293 was an issue for through association with `joins` for a long
time, but since #35864 through association with `left_joins` would also
be affected by the issue.
Implicit through table joins should be appeared before user supplied
joins, otherwise loading through association with joins will cause a
statement invalid error.
Fixes #36293.
```
% ARCONN=postgresql bundle exec ruby -w -Itest test/cases/associations/has_many_through_associations_test
.rb -n test_through_association_with_joins
Using postgresql
Run options: -n test_through_association_with_joins --seed 7116
# Running:
E
Error:
HasManyThroughAssociationsTest#test_through_association_with_joins:
ActiveRecord::StatementInvalid: PG::UndefinedTable: ERROR: missing FROM-clause entry for table "posts"
LINE 1: ... "comments_posts" ON "comments_posts"."post_id" = "posts"."i...
^
: SELECT "comments".* FROM "comments" INNER JOIN "comments" "comments_posts" ON "comments_posts"."post_id" = "posts"."id" INNER JOIN "posts" ON "comments"."post_id" = "posts"."id" WHERE "posts"."author_id" = $1
rails test test/cases/associations/has_many_through_associations_test.rb:61
Finished in 0.388657s, 2.5730 runs/s, 0.0000 assertions/s.
1 runs, 0 assertions, 0 failures, 1 errors, 0 skips
```
|
|\ \ \
| | | |
| | | | |
Use a single thread for all ConnectionPool Reapers
|
| | |/
| |/|
| | |
| | |
| | | |
Previously we would spawn one thread per connection pool, which ends up
being wasteful for apps with several connection pools.
|
|\ \ \
| | | |
| | | | |
Fix eager loading associations with string joins not to raise NoMethodError
|
| | | |
| | | |
| | | |
| | | | |
Fixes #34456.
|
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | | |
This partly reverts the effect of d1107f4d.
d1107f4d makes `touch` tracks the mutation whether the `touch` is
occurred by explicit or not.
Existing apps expects that the previous changes tracks only the changes
which is explicit action by users.
I'd revert the implicit `touch` mutation tracking since I'd not like to
break existing apps.
Fixes #36219.
|
| | | | |
|
|\ \ \ \
| | | | |
| | | | | |
Remove SQLite version support caveats [ci skip]
|
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | |
| | | | | |
Since d1a74c1e012ed96f7179e53b9190b7da0a369e11, Active Record requires
SQLite version 3.8.0 or greater, so savepoints and partial indexes are
always available.
That commit also added a runtime version check, so we can remove the
minimum version requirement from the internal adapter documentation.
|