Commit Graph

21803 Commits

Author SHA1 Message Date
Eileen M. Uchitelle
0c9e4069f7
Merge pull request #45751 from adrianna-chang-shopify/ac-build-change-column-default-definition
Define #build_change_column_definition for MySQL and PG
2022-08-04 08:37:11 -04:00
Alex Ghiculescu
bd0fdc8094 Add drop_enum command for Postgres 2022-08-03 18:50:43 -05:00
Adrianna Chang
7455336638 Define #build_change_column_definition for MySQL and PG
Define APIs on the MySQL and PostgreSQL connection adapters for building
ChangeColumnDefaultDefinition objects. These provide information on what a
column default change would look like, when called with the same arguments as
would be passed to #change_column_default.
2022-08-03 16:27:25 -04:00
eileencodes
58e6f11878
Fix indentation
I messed up copying and pasting this. Rubocop failures caught
this in https://github.com/rails/rails/runs/7658743379?check_suite_focus=true
2022-08-03 14:46:11 -04:00
eileencodes
25f97a66bd
Add support for if_exists option when removing a check constraint
The `remove_check_constraint` method now accepts an `if_exists` option. If set
to true an error won't be raised if the check constraint doesn't exist.

This commit is a combination of PR #45726 and #45718 with some
additional changes to improve wording, testing, and implementation.

Usage:

```ruby
remove_check_constraint :products, name: "price_check", if_exists: true
```

Fixes #45634

Co-authored-by: Margaret Parsa <mparsa@actbluetech.com>
Co-authored-by: Aditya Bhutani <adi_bhutani16@yahoo.in>
2022-08-03 14:39:54 -04:00
Jean Boussier
1288289ed0
Merge pull request #45697 from adrianna-chang-shopify/ac-change-column-default-mysql
Use SET DEFAULT when changing a column default in MySQL
2022-08-03 20:23:08 +02:00
Jean Boussier
e1f566a6f4
Merge pull request #45734 from fatkodima/fix-columnless-enums
Raise when defining an enum not backed by a database column
2022-08-03 20:20:39 +02:00
Adrianna Chang
b9b8852adc Use SET DEFAULT when changing a column default in MySQL
Aligns the SQL produced for changing a column default between MySQL and PostgreSQL.
MySQL is currently producing an <ALTER TABLE x CHANGE COLUMN y> query just to
change the default for a column, which is less efficient than using the SET DEFAULT syntax.

Additionally, extracts ChangeColumnDefaultDefinition and moves the SQL generation to the visitor class.
2022-08-03 11:16:06 -04:00
fatkodima
3a0d0f4bd8 Preserve collaction when changing column in MySQL 2022-08-03 13:09:25 +03:00
fatkodima
6c5fab0668 Raise when defining an enum not backed by a database column 2022-08-03 11:14:45 +03:00
Jean Boussier
408d061a80
Merge pull request #45720 from Shopify/find-or-create-or-find-by
find_or_create_by: handle race condition by finding again
2022-08-02 15:11:20 +02:00
fatkodima
cd3508607d Accept empty list of attributes for insert_all, insert_all! and upsert_all 2022-08-02 13:21:31 +03:00
Jean Boussier
023a3eb3c0 find_or_create_by: handle race condition by finding again
Using `create_or_find_by` in codepaths where most of the time
the record already exist is wasteful on several accounts.

`create_or_find_by` should be the method to use when most of the
time the record doesn't already exist, not a race condition safe
version of `find_or_create_by`.

To make `find_or_create_by` race-condition free, we can search
the record again if the creation failed because of an unicity
constraint.

Co-Authored-By: Alex Kitchens <alexcameron98@gmail.com>
2022-08-02 09:58:26 +02:00
Jean Boussier
765caa44a7
Merge pull request #45714 from simi/proper-verbose-cleanup
Store previous verbose setting before it can fail in tests.
2022-08-01 19:29:17 +02:00
Jean Boussier
7de5053923 Refactor ExtendedDeterministicQueries to not mutate the arguments
Ref: https://github.com/rails/rails/pull/41659

Mutating the attributes hash requires to workaround the mutation
in `find_or_create_by` etc.

One extra Hash dup is not big deal.
2022-08-01 16:21:33 +02:00
Josef Šimánek
4f4dd2ef02 Set collation for postgresql test DBs. 2022-07-31 16:23:00 +02:00
Josef Šimánek
bfdf158a15 Store previous verbose setting before it can fail in tests.
- thanks to hoisting it can be wrongly set to nil instead of previous value
2022-07-31 14:54:43 +02:00
fatkodima
438862b5d3 Support explicit schemas in PostgreSQL's create_enum 2022-07-31 00:12:07 +03:00
Matthew Draper
1adb6170d5 Add changelog entries for #44576 and #44591 2022-07-30 06:09:12 +09:30
Matthew Draper
72cdf1584a
Merge pull request #44591 from rails/defer-db-connect
Simplify adapter construction; defer connect until first use
2022-07-30 06:08:55 +09:30
Matthew Draper
7fe221d898
Merge pull request #44576 from rails/defer-db-verify
Defer verification of database connections
2022-07-30 06:08:34 +09:30
Eileen M. Uchitelle
b623494a29
Merge pull request #45685 from adrianna-chang-shopify/ac-build-create-join-table-definition
Extract `#build_create_join_table_definition`
2022-07-29 13:38:22 -04:00
Matthew Draper
91a3a2d0cc Don't expect rollback to cause a reconnect 2022-07-30 00:55:54 +09:30
Matthew Draper
e4193dee1d Be a bit clearer in the new-adapter-API argument error 2022-07-30 00:55:54 +09:30
Matthew Draper
0223967ab6 Drop default retry count to 1
This is enough to enable basic recovery for everyone by default, while
leaving more time-consuming repeated attempts for those who configure
them.
2022-07-30 00:55:54 +09:30
Matthew Draper
d56188dc7a We're still inside the transaction until the ROLLBACK has run
This previously made no difference, but it now saves us reconnecting to
run a ROLLBACK: because we're still inside a transaction at that moment,
we won't be #restorable?.
2022-07-30 00:55:54 +09:30
Matthew Draper
fe2846a154 Non-retryable exceptions also break connection verification 2022-07-30 00:55:54 +09:30
Matthew Draper
deec3004d8 Configure legacy-API-supplied connection before first use 2022-07-30 00:55:54 +09:30
Matthew Draper
0e9267767f Ensure a lost connection upon COMMIT fails "cleanly"
There's no point attempting to rollback in this case; we can instead
just invalidate the now-lost transaction.

Similarly, even though we can't immediately reconnect for a connection
failure mid-transaction, we can and should drop and prior verification
of the connection: the next out-of-transaction query attempt needs to
fix it, not assume it's working.
2022-07-30 00:55:54 +09:30
Matthew Draper
8551e64e24 Simplify adapter construction; defer connect until first use 2022-07-30 00:55:48 +09:30
Adrianna Chang
c59cbb55da Define #build_change_column_definition on connection adapters
Define APIs on the MySQL and PostgreSQL connection adapters for building
ChangeColumnDefinition objects. These provide information on what a
column change would look like, when called with the same arguments as
would be passed to #change_column.
2022-07-28 16:15:47 -04:00
Adrianna Chang
108c30e114 Extract build_create_join_table_definition
Exposes an API for building a TableDefinition for a join table operation.
2022-07-28 16:11:47 -04:00
Adrianna Chang
e91b6421ec Extract #build_add_column_definition
Exposes AlterTable schema definition for adding new columns through new API,
and stores ddl on the schema definition. Refactors existing #add_column method to use
this as an intermediate method to build the create add_column definition.
2022-07-28 15:19:29 -04:00
Eileen M. Uchitelle
f3339dfb95
Merge pull request #45630 from adrianna-chang-shopify/ac-extract-build-create-index-definition
Extract `#build_create_index_definition`
2022-07-28 14:51:32 -04:00
Adrianna Chang
54b45ff8e2 Extract #build_create_index_definition
Exposes CreateIndex schema definition through new API, and stores ddl
on the schema definition. Refactors existing #add_index methods to use
this as an intermediate method to build the create index definition.
2022-07-28 13:42:38 -04:00
Eileen M. Uchitelle
2e8f4cb062
Merge pull request #45669 from adrianna-chang-shopify/ac-allow-change-table-to-specify-base
Allow base for `Table` schema definition to be injected into `#change_table`
2022-07-27 13:58:21 -04:00
fatkodima
fcd90558b7 Add missing test ensuring no subqueries for whole table batching 2022-07-27 17:37:46 +03:00
Adrianna Chang
1f777620a8 Allow base for Table schema definition to be injected into #change_table 2022-07-27 09:56:47 -04:00
Gannon McGibbon
8b94e87c11
Merge pull request #45659 from gmcgibbon/parent_option_default
Parent option defaults
2022-07-26 18:35:29 -05:00
Gannon McGibbon
e1635ff4a7 Show default parent classes for generators in help texts
Print default parent class for controller, job, and model generators.

Before:

[--parent=PARENT]               # The parent class for the generated job

After:

[--parent=PARENT]               # The parent class for the generated job
                                # Default: ApplicationJob
2022-07-26 18:13:02 -05:00
Matthew Draper
57bc28f728 Add new tests for deferred connection verification and auto-reconnect 2022-07-27 02:15:15 +09:30
Jonathan Hefner
e2d9747123 Fix update_all API doc [ci-skip]
Multi-line list items must be indented, and inline code must be quoted
using `+` or `<tt>`.  (RDoc does not support backticks.)
2022-07-26 10:38:37 -05:00
Matthew Draper
6693e5fc9a Deadlocks inside transactions are functionally not retryable
Even if we think the deadlocking query could be retried, the original
deadlock will have either broken or already rolled back our transaction.
2022-07-26 22:07:36 +09:30
Matthew Draper
3cc2f8ac77 Check #reconnect_can_restore_state? once, before running block
The block can't affect reconnectability, because we'll be re-running it
anyway.

Also, only #reconnect! once per query, to avoid squaring the total
number of permitted retries while attempting to query a pathologically
flakey server.
2022-07-26 22:07:35 +09:30
Matthew Draper
02f5de1bc9 Add retry handling to connection establishment too 2022-07-26 22:07:35 +09:30
Matthew Draper
da52b0d954 Separate two groups of retryable DB exceptions
Connectivity issues need a reconnect to be retried, but there are also
in-server errors that can also be retried (lock timeouts and deadlocks).

To handle this better, we move translation into #with_raw_connection:
it's a much better representation of the boundary between the underlying
adapter library and Active Record's abstractions anyway. (It doesn't
know about the query being run, though, so we let #log enrich that into
the exception later.)
2022-07-26 22:07:35 +09:30
Matthew Draper
b9f44e66ba Restore transactions in materialized state where appropriate
We may be restoring a connection after #with_raw_connection has already
passed #materialize_transactions, so it's important we eagerly return
things to exactly the state they had before.
2022-07-26 22:07:35 +09:30
Matthew Draper
129bfa193c Default most internal/schema queries to retryable 2022-07-26 22:07:35 +09:30
Matthew Draper
35d3ae3298 Switch Postgres statement pool to use the AR connection
We're still ultimately accessing the raw connection directly, but this
is necessary to keep the statement pool working across full reconnects.
2022-07-26 22:07:35 +09:30
Matthew Draper
542f0951dd Automatically reconnect to database mid-request
So far this is just infrastructure: no errors are considered retryable,
and no real queries are marked retryable.

Even in this state, we can drop connection verification from checkout,
and defer it until the first query is ready. But the more interesting
within-reach win will be when 'BEGIN' is retryable, and we can recognise
connectivity-related exceptions.
2022-07-26 22:07:35 +09:30