はじめに
production環境のUnicornが不定期にアクセスできなくなる問題が発生しました。
Unicornのプロセスは起動しているものの、ブラウザでアクセスすると502が返されます。
環境
- AWS
- Ubuntu16.04
- Unicorn 5.3.0
- Rails 5.1
- Ruby 2.4.1
発生したエラー
Unicorn.log
には以下が出力されていました。
/home/ubuntu/.rbenv/versions/2.4.1/lib/ruby/gems/2.4.0/gems/unicorn-5.3.0/lib/unicorn/http_request.rb:80:in `parse': method `hash' called on hidden T_ARRAY object (0x0055645c4cf7a0 flags=0x1a067) (NotImplementedError)
from /home/ubuntu/.rbenv/versions/2.4.1/lib/ruby/gems/2.4.0/gems/unicorn-5.3.0/lib/unicorn/http_request.rb:80:in `read'
from /home/ubuntu/.rbenv/versions/2.4.1/lib/ruby/gems/2.4.0/gems/unicorn-5.3.0/lib/unicorn/http_server.rb:606:in `process_client'
from /home/ubuntu/.rbenv/versions/2.4.1/lib/ruby/gems/2.4.0/gems/unicorn-5.3.0/lib/unicorn/http_server.rb:702:in `worker_loop'
from /home/ubuntu/.rbenv/versions/2.4.1/lib/ruby/gems/2.4.0/gems/unicorn-5.3.0/lib/unicorn/http_server.rb:549:in `spawn_missing_workers'
from /home/ubuntu/.rbenv/versions/2.4.1/lib/ruby/gems/2.4.0/gems/unicorn-5.3.0/lib/unicorn/http_server.rb:563:in `maintain_worker_count'
from /home/ubuntu/.rbenv/versions/2.4.1/lib/ruby/gems/2.4.0/gems/unicorn-5.3.0/lib/unicorn/http_server.rb:293:in `join'
from /home/ubuntu/.rbenv/versions/2.4.1/lib/ruby/gems/2.4.0/gems/unicorn-5.3.0/bin/unicorn_rails:209:in `<top (required)>'
from /home/ubuntu/.rbenv/versions/2.4.1/bin/unicorn_rails:22:in `load'
from /home/ubuntu/.rbenv/versions/2.4.1/bin/unicorn_rails:22:in `<main>'
考えられる原因
エラーログに出ているT_ARRAY
という変数は、unicorn/bindings/ruby/unicorn_gem/ext/unicorn.c
が使っている変数のようです(214行目)
https://github.com/unicorn-engine/unicorn/blob/master/bindings/ruby/unicorn_gem/ext/unicorn.c
213行目のUC_X86_REG_TR
で調べてみると、UC_HOOK_MEM_FETCH_INVALID
の中にあり、
メモリのフェッチが無効?という事象のようです。。
http://cpansearch.perl.org/src/VIKAS/UnicornEngine-0.02/lib/UnicornEngine.pm
また、herokuで類似したエラーが出てる人がいました。
Google翻訳によると、以下が原因とのこと。
異なるRubyバージョンのオブジェクトからのバージョンの不一致
またはC拡張によって引き起こされるメモリの破損
unicorn Ruby/Rack server user+dev discussion/patches/pulls/bugs/help
また、Unicorn5.3.0にはGC関連の問題があるそうです。
unicorn 5.3.1 / 2017-10-03 19:03 UTC
unicorn 5.3.1 / 2017-10-03 19:03 UTC
This release fixes an occasional GC problem introduced in v5.3.0
to reduce global variable overhead (commit 979ebcf91705709b)Thanks to Xuanzhong Wei for the patch which lead to this release:
https://bogomips.org/unicorn-public/20171003182054.76392-1-azrlew@gmail.com/T/#u
https://bogomips.org/unicorn-public/20171003145718.30404-1-azrlew@gmail.com/T/#uXuanzhong Wei (1):
fix GC issue on rb_global_variable array
上記を踏まえ、Unicornを5.3.1に更新することにしました。
事前準備
Gemfile
のバージョンを固定化する。
gem 'unicorn', '5.3.1'
アップデートの失敗例
bundle install
で入れようとすると、lockファイルと違うと怒られるので注意。
$ bundle install --without development test staging
The dependency tzinfo-data (>= 0) will be unused by any of the platforms Bundler is installing for. Bundler is installing for ruby but the dependency is only for x86-mingw32, x86-mswin32, x64-mingw32, java. To add those platforms to the bundle, run `bundle lock --add-platform x86-mingw32 x86-mswin32 x64-mingw32 java`.
Fetching gem metadata from https://rubygems.org/..........
Fetching gem metadata from https://rubygems.org/.
You have requested:
unicorn = 5.3.1
The bundle currently has unicorn locked at 5.3.0.
Try running `bundle update unicorn`
If you are updating multiple gems in your Gemfile at once,
try passing them all to `bundle update`
アップデートの成功例
bundle update unicorn
で更新する。
$ bundle update unicorn
・・・略・・・
Fetching unicorn 5.3.1 (was 5.3.0)
Installing unicorn 5.3.1 (was 5.3.0) with native extensions
おわりに
これでひとまず様子を見てみることにします。
エラーが改善されることを期待します。