README.md in strong_migrations-0.5.1 vs README.md in strong_migrations-0.6.0
- old
+ new
@@ -1,9 +1,11 @@
# Strong Migrations
Catch unsafe migrations in development
+Supports for PostgreSQL, MySQL, and MariaDB
+
:tangerine: Battle-tested at [Instacart](https://www.instacart.com/opensource)
[![Build Status](https://travis-ci.org/ankane/strong_migrations.svg?branch=master)](https://travis-ci.org/ankane/strong_migrations)
## Installation
@@ -84,11 +86,11 @@
4. Deploy and run migration
### Adding a column with a default value
-Note: This operation is safe in Postgres 11+.
+Note: This operation is safe in Postgres 11+, MySQL 8.0.12+, and MariaDB 10.3.2+
#### Bad
Adding a column with a default value to an existing table causes the entire table to be rewritten.
@@ -142,14 +144,14 @@
```ruby
class BackfillSomeColumn < ActiveRecord::Migration[6.0]
disable_ddl_transaction!
- def change
+ def up
User.unscoped.in_batches do |relation|
relation.update_all some_column: "default_value"
- sleep(0.1) # throttle
+ sleep(0.01) # throttle
end
end
end
```
@@ -179,12 +181,18 @@
add_index :users, :some_column, algorithm: :concurrently
end
end
```
-If you forget `disable_ddl_transaction!`, the migration will fail. Also, note that indexes on new tables (those created in the same migration) don’t require this. Check out [gindex](https://github.com/ankane/gindex) to quickly generate index migrations without memorizing the syntax.
+If you forget `disable_ddl_transaction!`, the migration will fail. Also, note that indexes on new tables (those created in the same migration) don’t require this.
+With [gindex](https://github.com/ankane/gindex), you can generate an index migration instantly with:
+
+```sh
+rails g index table column
+```
+
### Adding a reference
#### Bad
Rails adds an index non-concurrently to references by default, which is problematic for Postgres.
@@ -612,40 +620,54 @@
StrongMigrations.error_messages[:add_column_default] = "Your custom instructions"
```
Check the [source code](https://github.com/ankane/strong_migrations/blob/master/lib/strong_migrations.rb) for the list of keys.
-## Postgres-Specific Features
+## Analyze Tables
-### Analyze Tables
-
Analyze tables automatically (to update planner statistics) after an index is added. Create an initializer with:
```ruby
StrongMigrations.auto_analyze = true
```
-### Lock Timeout
+## Target Version
-It’s a good idea to set a lock timeout for the database user that runs migrations. This way, if migrations can’t acquire a lock in a timely manner, other statements won’t be stuck behind it. Here’s a great explanation of [how lock queues work](https://www.citusdata.com/blog/2018/02/15/when-postgresql-blocks/).
+If your development database version is different from production, you can specify the production version so the right checks are run in development.
-```sql
-ALTER ROLE myuser SET lock_timeout = '10s';
+```ruby
+StrongMigrations.target_postgresql_version = "10"
+StrongMigrations.target_mysql_version = "8.0.12"
+StrongMigrations.target_mariadb_version = "10.3.2"
```
-There’s also [a gem](https://github.com/gocardless/activerecord-safer_migrations) you can use for this.
+For safety, this option only affects development and test environments. In other environments, the actual server version is always used.
-### Target Version
+## Timeouts
-If your development database version is different from production, you can specify the production version so the right checks are run in development.
+It’s a good idea to set a long statement timeout and a short lock timeout for migrations. This way, migrations can run for a while, and if a migration can’t acquire a lock in a timely manner, other statements won’t be stuck behind it.
+You can use:
+
```ruby
-StrongMigrations.target_postgresql_version = 10 # or 9.6, etc
+StrongMigrations.statement_timeout = 1.hour
+StrongMigrations.lock_timeout = 10.seconds
```
-For safety, this option only affects development and test environments. In other environments, the actual server version is always used.
+Or set the timeouts directly on the database user that runs migrations. For Postgres, use:
+```sql
+ALTER ROLE myuser SET statement_timeout = '1h';
+ALTER ROLE myuser SET lock_timeout = '10s';
+```
+
+Note: If you use PgBouncer in transaction mode, you must set timeouts on the database user.
+
+## Permissions
+
+We recommend using a [separate database user](https://ankane.org/postgres-users) for migrations when possible so you don’t need to grant your app user permission to alter tables.
+
## Additional Reading
- [Rails Migrations with No Downtime](https://pedro.herokuapp.com/past/2011/7/13/rails_migrations_with_no_downtime/)
- [PostgreSQL at Scale: Database Schema Changes Without Downtime](https://medium.com/braintree-product-technology/postgresql-at-scale-database-schema-changes-without-downtime-20d3749ed680)
@@ -660,10 +682,10 @@
- [Report bugs](https://github.com/ankane/strong_migrations/issues)
- Fix bugs and [submit pull requests](https://github.com/ankane/strong_migrations/pulls)
- Write, clarify, or fix documentation
- Suggest or add new features
-To get started with development and testing:
+To get started with development:
```sh
git clone https://github.com/ankane/strong_migrations.git
cd strong_migrations
bundle install