| Commit message (Collapse) | Author | Age | Files | Lines |
|
|
|
| |
`Arel::Attributes.for` is no longer used since https://github.com/rails/arel/pull/196.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Each `visit o, collector` allocates one extra array due to
receiving args by splat array.
https://github.com/rails/rails/blob/2c3332cc4c0fa77dbe2e13e8a792f80fbd8f4ad3/activerecord/lib/arel/visitors/visitor.rb#L27-L29
Currently 1,000 times `User.where(id: 1).to_sql` allocates 13,000
arrays in `visitor.accept`. This avoids receiving args by splat array,
it makes `visitor.accept` no array allocation.
```ruby
ObjectSpace::AllocationTracer.setup(%i{path line type})
pp ObjectSpace::AllocationTracer.trace {
1_000.times { User.where(id: 1).to_sql }
}.select { |k, _| k[2] == :T_ARRAY && k[0].end_with?("visitor.rb", "to_sql.rb") }
```
Before (2c3332cc4c0fa77dbe2e13e8a792f80fbd8f4ad3):
```
{["~/rails/activerecord/lib/arel/visitors/to_sql.rb",
18,
:T_ARRAY]=>[1000, 0, 0, 0, 0, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/determine_if_preparable_visitor.rb",
11,
:T_ARRAY]=>[1000, 0, 0, 0, 0, 0],
["~/rails/activerecord/lib/arel/visitors/visitor.rb",
12,
:T_ARRAY]=>[1000, 0, 0, 0, 0, 0],
["~/rails/activerecord/lib/arel/visitors/to_sql.rb",
788,
:T_ARRAY]=>[3000, 0, 0, 0, 0, 0],
["~/rails/activerecord/lib/arel/visitors/to_sql.rb",
794,
:T_ARRAY]=>[3000, 0, 0, 0, 0, 0],
["~/rails/activerecord/lib/arel/visitors/to_sql.rb",
156,
:T_ARRAY]=>[1000, 0, 0, 0, 0, 0],
["~/rails/activerecord/lib/arel/visitors/to_sql.rb",
443,
:T_ARRAY]=>[1000, 0, 0, 0, 0, 0],
["~/rails/activerecord/lib/arel/visitors/to_sql.rb",
603,
:T_ARRAY]=>[1000, 0, 0, 0, 0, 0],
["~/rails/activerecord/lib/arel/visitors/to_sql.rb",
611,
:T_ARRAY]=>[1000, 0, 0, 0, 0, 0]}
```
After (this change):
```
{}
```
|
|
|
|
|
|
|
| |
Tables in tests are not always empty so `klass.first` does not always
find last created record.
Fixes #36479.
|
|
|
|
| |
https://buildkite.com/rails/rails/builds/61744#f12cc6cf-7458-4131-917a-9735615f6259/999-1010
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
If we put the `while_preventing_writes` on the connection then the
middleware that sends reads to the primary and ensures they can't write
will not work. The `while_preventing_writes` will only be applied to the
connection which it's called on - which in the case of the middleware is
Ar::Base.
This worked fine if you called it directly like
`OtherDbConn.connection.while_preventing_writes` but Rails didn't have a
way of knowing you wanted to call it on all the connections.
The change here moves the `while_preventing_writes` method from the
connection to the handler so that it can block writes to all queries for
that handler. This will apply to all the connections associated with
that handler.
|
|\
| |
| |
| |
| | |
eileencodes/move-schema-migration-to-migration-context
Move SchemaMigration to migration_context
|
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| | |
This PR moves the `schema_migration` to `migration_context` so that we
can access the `schema_migration` per connection.
This does not change behavior of the SchemaMigration if you are using
one database. This also does not change behavior of any public APIs.
`Migrator` is private as is `MigrationContext` so we can change these as
needed.
We now need to pass a `schema_migration` to `Migrator` so that we can
run migrations on the right connection outside the context of a rake
task.
The bugs this fixes were discovered while debugging the issues around
the SchemaCache on initialization with multiple database. It was clear
that `get_all_versions` wouldn't work without these changes outside the
context of a rake task (because in the rake task we establish a
connection and change AR::Base.connection to the db we're running on).
Because the `SchemaCache` relies on the `SchemaMigration` information we
need to make sure we store it per-connection rather than on
ActiveRecord::Base.
[Eileen M. Uchitelle & Aaron Patterson]
|
|\ \
| |/
|/|
| |
| | |
albertoalmagro/alberto/reverse-column-is-reversible
[ci skip] Update docs as `remove_column` can be reversed
|
| |
| |
| |
| |
| | |
As `remove_column` can be reversed when a type is provided this example
was not accurate anymore.
|
| | |
|
|/
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Currently 1,000 transactions creates 10,000 objects regardless whether
it is necessary or not.
This makes allocation on demand in transactions, now 1,000 transactions
creates required 5,000 objects only by default.
```ruby
ObjectSpace::AllocationTracer.setup(%i{path line type})
pp ObjectSpace::AllocationTracer.trace {
1_000.times { User.create }
}.select { |k, _| k[0].end_with?("transaction.rb") }
```
Before (95d038f):
```
{["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
209,
:T_HASH]=>[1000, 0, 715, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
210,
:T_OBJECT]=>[1000, 0, 715, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
210,
:T_HASH]=>[1000, 0, 715, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
80,
:T_OBJECT]=>[1000, 0, 715, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
8,
:T_ARRAY]=>[1000, 0, 715, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
81,
:T_ARRAY]=>[1000, 0, 715, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
289,
:T_STRING]=>[1000, 0, 714, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
116,
:T_ARRAY]=>[1000, 0, 714, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
120,
:T_ARRAY]=>[1000, 0, 714, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
121,
:T_HASH]=>[1000, 0, 714, 0, 1, 0]}
```
After (this change):
```
{["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
213,
:T_HASH]=>[1000, 0, 739, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
214,
:T_OBJECT]=>[1000, 0, 739, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
214,
:T_HASH]=>[1000, 0, 739, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
81,
:T_OBJECT]=>[1000, 0, 739, 0, 1, 0],
["~/rails/activerecord/lib/active_record/connection_adapters/abstract/transaction.rb",
304,
:T_STRING]=>[1000, 0, 738, 0, 1, 0]}
```
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
* Make ActiveRecord `ConnectionPool.connections` thread-safe.
ConnectionPool documentation is clear on the need to synchronize
access to @connections but also states that public methods do not
require synchronization. Existing code exposed @connections
directly via attr_reader. The fix uses synchronize() to lock
@connections then returns a copy to the caller using Array.dup().
Includes comments on the connections method that thread-safe access
to the connections array does not imply thread-safety of accessing
methods on the actual connections.
Adds a test-case that modifies the pool using a supported method
in one thread while a second thread accesses pool.connections.
The test fails without this patch.
Fixes #36465.
* Update activerecord/test/cases/connection_pool_test.rb
[jeffdoering + Rafael Mendonça França]
|
|
|
|
|
|
|
| |
"schema_migrations" table may be hard dropped before, so the reset
migration version should be done in ensure block.
https://buildkite.com/rails/rails/builds/61697#18d6f3ac-2257-4f4b-8efc-4010464c4d9a/999-1011
|
|
|
|
| |
https://buildkite.com/rails/rails/builds/61695#373bb1a7-677f-49ec-95e7-a92467fefd60/1076-1084
|
|
|
|
|
|
|
|
|
| |
"schema_migrations" is hard dropped by some existing tests, so testing
migration in using transactional tests may cause implicit creation and
rollback "schema_migrations" table, it makes migration tests flaky.
https://buildkite.com/rails/rails/builds/61692#42383249-30be-4508-b1fb-a7bb27600c8e/999-1010
https://buildkite.com/rails/rails/builds/61694#6e462ad3-41d8-4e26-95ce-728495b0ac64/999-1010
|
|\
| |
| | |
Enable `Layout/EmptyLinesAroundAccessModifier` cop
|
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| | |
We sometimes say "✂️ newline after `private`" in a code review (e.g.
https://github.com/rails/rails/pull/18546#discussion_r23188776,
https://github.com/rails/rails/pull/34832#discussion_r244847195).
Now `Layout/EmptyLinesAroundAccessModifier` cop have new enforced style
`EnforcedStyle: only_before` (https://github.com/rubocop-hq/rubocop/pull/7059).
That cop and enforced style will reduce the our code review cost.
|
| |
| |
| |
| |
| |
| | |
`table_exists?` is already exist in `ModelSchema`.
https://github.com/rails/rails/blob/5cab344494c340ea82a35b46efa06b94f0b7730b/activerecord/lib/active_record/model_schema.rb#L339-L341
|
|/
|
|
| |
Otherwise `Model.table_exists?` returns the staled cache result.
|
|\
| |
| | |
Add support for multiple databases to `rails db:abort_if_pending_migrations`
|
| | |
|
|\ \
| |/
|/|
| |
| | |
kamipo/allow_column_name_with_simple_function_call
Allow column name with function (e.g. `length(title)`) as safe SQL string
|
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| | |
Currently, almost all "Dangerous query method" warnings are false alarm.
As long as almost all the warnings are false alarm, developers think
"Let's ignore the warnings by using `Arel.sql()`, it actually is false
alarm in practice.", so I think we should effort to reduce false alarm
in order to make the warnings valuable.
This allows column name with function (e.g. `length(title)`) as safe SQL
string, which is very common false alarm pattern, even in the our
codebase.
Related 6c82b6c99, 6607ecb2a, #36420.
Fixes #32995.
|
|/ |
|
| |
|
|
|
|
|
| |
`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
|