始めに
私は現在、業務でRuby on Railsを用いてアプリケーションを開発しています。
先日、RailsのアプリケーションをHerokuからAWSのEC2に移行致しました。
その際、本番環境同等の検証環境でRailsアプリのlog直下のログファイルにログが出力されなくなる現象が起こりました。
検証環境のログが追えないのはテストなどの際に非常に影響が出るため、原因を調査したのでその過程についてまとめたいと思います。
環境情報
Ruby:2.2.5
Rails:4.2.6
実行環境:AWS EC2(Amazon Linux 2016.03)
原因調査
HerokuからEC2に移行した結果、開発環境では正常にlog直下のdevelopment.logにログが出力されるが、検証環境ではlog直下のintegration_test.logに出力されないのが今回の現象です。
そのため、サーバ環境用のGemないしは検証環境での設定ファイルであるintegration_test.rbがRails.loggerを標準出力となるように上書きしているのではないかと考えました。
(標準出力になるとコンソールのみに出力され、ログファイルに出力されなくなります。)
①設定ファイル
設定ファイルをくまなく確認しても、Rails.loggerを上書きしている箇所は見つからず、
ここが原因ではないと判明しました。
②Gem
サーバ環境用のGemを一つ一つ調べていくと、rails_12factorというGemがRails.loggerを標準出力するように上書きしていました。
rails_12factorとは何か
rails_12factorとはRailsアプリケーションをHerokuで動作をさせることを目的としているGemで、
Railsアプリケーションを本番環境などのサーバ上で動かすためのアセットがまとまったGemである「rails_serve_static_assets」とHerokuの本番環境ではログを標準出力にストリームする必要があるためのloggingのためのGemである「rails_stdout_logging」が内包されたGemです。
今回はHerokuで運用していた際に必要だったrails_12factorがそのまま残っていたため、EC2でもログが標準出力されてしまい、log直下のintegration_test.logに何も出力されてなかったようです。
解決策
①ActiveRecordのログのみ表示
設定ファイル内に新しくloggerを作成しても、rails_12factorで上書きされてしまいますが、
ActiveRecordのログならば上書きされません。
そのため、設定ファイルに以下のコードを追記すれば、検証環境でもActiveRecordのログは正常にログファイルに出力されました。
ActiveRecord::Base.logger = Logger.new("log/integration_test.log")
ActiveRecord::Base.logger.level = 0 # 任意のログレベル
しかし、この方法ではActiveRecordのログだけが見られるようになり、Railsのログが見たいという根本的な解決策にはなっていないため、今回は②の対応策を取りました。
②使用するGemの変更
そもそも今回は検証環境でも本番環境でもHerokuを使用しないため、rails_12factorを使用する必要はありません。サーバ上で動作させるためのアセットのGemである「rails_serve_static_assets」さえあれば良いので、Gemfileを下記のように書き換えました。
group :integration_test, :production do
# gem 'rails_12factor', '0.0.3'
gem 'rails_serve_static_assets', '0.0.5'
end
こちらで試してみたところ、無事Rialsのログがlog直下のintegration_test.logに出力されるようになりました。
総括
まとめ
Herokuを使わないサーバ上の検証・本番環境ならば、上記の「rails_serve_static_assets」を用いることでアプリケーション自体も正常に動作し、ログをそれぞれlog直下のファイルに出力されます。
しかし、Herokuを使う際は、ログを標準出力にする必要があるため、上記のような方法は取れません。
今後
今までログがどのように出力されているのかを意識したことがなかったので、良い勉強になりました。
今後はRails.loggerそのものの知識をより深めていきたいです。
参考サイト
Github-rails_12factor
Github-rails_serve_static_assets
Github-rails_stdout_logging
余談
12factorとは何か
本記事中に何度も出てきた「rails_12factor」の12factorとは、Herokuの創始者であるアダム・ウィギンスが提唱したインフラの運用を考えた際にアプリケーションが満たしているべき12の要素です。
具体的には、下記の4つを目的とした考え方です。
- OSへの依存関係を明確にして、移植性を最大にする。
- クラウドへのデプロイを前提にしており、サーバ管理やシステム管理を不要なものとする。
- 開発環境と本番環境の差異を少なくし、継続的なデプロイを可能にする。
- アーキテクチャや開発ツールを大幅に変更することなく、スケーラブルを行う。
また、12の要素は本家のサイトを参考にしてください。
Heroku上のアプリケーションはこの12の要素に沿っていくべきだと考えられており、Herokuで運用されるアプリケーションにRuby on Railsのものが多いのは、この12の要素に非常にマッチしているためです。
Rails5と12factor
2016年7月にリリースされたRails5では、この12の要素が初めから動作するように設計されているため、「rails_12factor」のGemを入れる必要がなく、サーバ上にデプロイすることが出来ます。
しかし、Heroku上にデプロイする際は、loggerを標準出力に変更するように設定ファイルの変更が必要なので、注意が必要です。