デプロイ後のテーブルの変更とデータベースのリセットについて

# はじめに
通っているプログラミングスクールで初めてのチーム開発を行いました。データベース設計については十分に検討したつもりでしたが、開発する中でカラム変更や本番環境のデータベースをリセットしたい！！と思うことがありました。そこで、自分の備忘録として記録を残そうと思います。
なお、デプロイ後のデータベースのリセットは本来あってはならないことであると思います。参考にされる方は、プログラミング初心者が書いた記事であることを忘れないで下さい。

# 開発環境
AWS EC2
Capistranoによる自動デプロイ
Capistrano Version: 3.14.0 (Rake Version: 13.0.1)
Rails 5.2.4.3
ruby 2.5.1p57 (2018-03-29 revision 63029) [x86_64-darwin19]
mysql  Ver 14.14 Distrib 5.6.47, for osx10.15 (x86_64) using  EditLine wrapper

# 参考にさせていただいた記事
[【Rails】本番環境デプロイでよく使うコマンド集！AWS/unicorn/nginx/Capistrano使用](https://qiita.com/15grmr/items/7ad36caa82a0fa27c4bd) @15grmr様
[Ruby on Rails カラムの追加と削除](https://qiita.com/azusanakano/items/a2847e4e582b9a627e3a) @azusanakano様
[【Rails】カラムのデータ型変更方法](https://qiita.com/yana_dev/items/c96594bbea3329ef0fec) @yana_dev様

# これから書くこと

- テーブルのデータ型の変更とカラムの削除と追加
- 本番環境のデータベースのリセット

# テーブルのデータ型の変更とカラムの削除と追加
基本的にマイグレーションファイルを追加することで対応します。
私はこれまでローカル環境では、マイグレーションファイルをrollbackして、書き換えて再度migrateという方法をとってきましたが、これはあまり良くないようです。というのもマイグレーションファイルはテーブルの変更履歴という側面もあるようなので、書き換えるのは履歴が改竄されるということになるようです。
また、チーム開発においては、勝手にマイグレーションの記述を書き換えると、、、
①他のメンバーのブランチに反映されない
②他のメンバーがブランチのマージを行う前に対象のマイグレーションファイルをrollbackしてもらわないといけない（そうなると、チームメンバーのローカルのデータベースのレコードを削除することになりかねない）などの問題も発生します。

そこでカラム変更のマイグレーションファイルを作成して対応します。

## CASE1 データ型を変更したい
今回は、私が実際に行った変更を例に挙げます。addressesテーブルのprefictureカラムのデータ型を「string」から「integer」に変更したいということがありました。以下の記述でマイグレーションファイルを作成します。

```:ターミナル
$ rails g migration change_data_preficture_to_adresses
```

生成されたマイグレーションファイルに記述します。

```ruby:db/migrate/*****_change_data_preficture_to_addresses.rb
class ChangeDataPrefictureToAddresses < ActiveRecord::Migration[5.2]
  def change
    change_column :addresses, :preficture, :integer
  end
end
```

Capistranoによる自動デプロイであれば毎回自動デプロイを行うたびにmigrateを行うようなので、これで本番環境のカラムのデータ型を変更できます。

## CASE2 カラムの削除と追加をしたい
これも同様にマイグレーションファイルを生成して対応します。カラム削除用とカラム追加用の２つのファイルを使用します。同じく私の実例ということで、cardsテーブル内のuser_idが外部キーではなく、通常のinteger型のカラムで作られていたというシチュエーションです。

まずは、user_idカラムを削除します。

```:ターミナル
$ rails g migration remove_user_id_from_cards
```

生成されたマイグレーションファイルに記述します。

```ruby:db/migrate/*****_remove_user_id_from_cards.rb
class RemoveUserIdFromCards < ActiveRecord::Migration[5.2]
  def change
    remove_column :cards, :user_id, :integer
  end
end
```

次にカラム追加用のマイグレーションファイルを生成します。今回は外部キーのカラムなので記述が若干異なります。

```:ターミナル
$ rails g migration add_user_ref_to_cards
```
refは、外部キーのreference型を指します。

```ruby:
class AddUserRefToCards < ActiveRecord::Migration[5.2]
  def change
    add_reference :cards, :user, foreign_key: true
  end
end
```

同じくCapistranoによる自動デプロイを行えば、カラムを削除して追加することができます。

## 本番環境のデータベースをリセットしたい
開発の途中で本番環境用のデータベースをリセットしたいということも発生すると思います。
私も本番環境用のアカウントを控えておらず、ログインできなくなったり、その結果以前登録した（画像のリンク切れ）商品が削除できなかったり、色々やらかしました。

そこで本番環境のデータベースのリセットを実行しました。

```:ターミナル
$ bundle exec cap production deploy
```

一旦、Capistranoによる自動デプロイを終わらせておきます。
そして、AWSにログインします。

```:ターミナル
$ ssh -i ~/.ssh/*******.pem ec2-user@XX.XXX.XXX.XX

```

「*******」にはpemファイルの名前を、「XX.XXX.XXX.XX」にはElastic IPを入力します。
次に「current」へ移動します。

```:ターミナル
$ cd  /var/www/アプリケーション名/current
```

「current」にアクセスできたらここからデータベース操作に入ります。
まずは、データベースをdropします。

```:ターミナル
$ RAILS_ENV=production DISABLE_DATABASE_ENVIRONMENT_CHECK=1 bundle exec rake db:drop
```

本番環境用のデータベースがなくなってしまったので、再度データベースを作ります。

```:ターミナル
$ rake db:create RAILS_ENV=production
```

マイグレーションを実施します。

```:ターミナル
$ rake db:migrate RAILS_ENV=production
```

seedsファイルがあれば、読み込ませます。

```:ターミナル
$ rake db:seed RAILS_ENV=production
```

ここまででデータベースの完全リセットは終了です。
AWSからのログアウトも忘れずに。

```:ターミナル
$ exit
```