概要
HerokuのPostgreSQLアドオンは費用が高めです。そこで、よりコスト効率の良いMySQLのJawsDBに移行する方法を紹介します。
ローカル環境の設定変更
主に修正するファイルはGemfile
とconfig/database.yml
です。
ファイルの修正手順
-
Gemfile:
pg
gemをコメントアウトし(念のため保持)、gem "mysql2", "~> 0.5"
を追加します。ここで"~> 0.5"
を指定する理由は、新規にrails new -d mysql
で作成したプロジェクトに同じバージョンが指定されていたためです。 -
database.yml: MySQLを使うために、新規に作成したRailsプロジェクトの設定を参考に変更します。違いはdefaultの設定だけだったのでそこだけ変更します。
変更前:
default: &default adapter: postgresql encoding: unicode pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>
変更後:
default: &default adapter: mysql2 encoding: utf8mb4 pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %> username: root password: socket: /tmp/mysql.sock
その後、rails db:create
を実行し、データベースを作成します。その後、rails db:migrate
でマイグレーションを実行し、rails s
でサーバーを起動します。正常に立ち上がれば設定は成功です。
エラー処理
もし以下のようなエラーが発生した場合は、前のインスタンスがまだ稼働している可能性があります。この場合は、lsof -i :3000
でプロセスIDを調べ、kill -9 [PID]
で該当プロセスを終了させます。
Address already in use - bind(2) for "127.0.0.1" port 3000 (Errno::EADDRINUSE)
データの削除
MySQLでの動作が確認できたら、PostgreSQLのデータを削除します。私の場合は個人開発で利用者がほとんどいないため、安心してデータを削除しました。削除するには、設定ファイルを元に戻した後、rails db:drop
でデータベースを削除しました。
Herokuでの設定
次に、Herokuでの設定を行います。
最後に変更をデプロイします。以下のようなログが表示されれば、データベースの変更が適用されたことになります。
- 実際にアプリケーションを起動して動作を確認し、問題がなければ完了です。
追記
デプロイした後、heroku run rake db:migrate
を実行するとエラーになります。この問題を解決するためには、以下の2点を修正する必要があります。
1. database.yml
のproduction設定の変更
database.yml
ファイルのproductionセクションにおいて、JAWSDB_URL
環境変数からデータベースのURLを取得するように設定します。これにより、データベース名やパスワードなどの情報が一括で設定されます。
production:
<<: *default
url: <%= ENV['JAWSDB_URL'] %>
2. Herokuの環境変数設定の変更
Herokuの設定をheroku config
で確認すると、JAWSDB_URL
環境変数がmysql:~~~
となっていることが分かります。Railsではmysql2
アダプターを使用しているため、このURLをmysql2
プロトコルに変更する必要があります。これは、既存のURLをコピーし、プロトコル部分に2
を付け加えることで行います。以下のコマンドを実行します。
heroku config:set JAWSDB_URL="mysql2://~~~"
これらの変更を行うことで、Heroku本番環境でのマイグレーションが正常に機能するはずです。
参考資料