CentOS 7でNginx、Unicornにハマる

今まで何度も使ったことある設定なのに、502 Bad Gatewayになった。

エラーログには以下が出ているが、socketファイルは存在して、パーミッションも問題なし。

[crit] 27195#0: *2 connect() to unix:/tmp/unicorn-example.socket failed (2: No such file or directory) while connecting to upstream, client: IPアドレス, server: example.com, request: "GET / HTTP/1.1", upstream: "http://unix:/tmp/unicorn-example.socket:/", host: "example.com"

困り果てていたら、RedmineをCentOS 7上で動かすーUnicornとNginx編 - ソフトウェアエンジニアリング - Torutk に辿り着いた。
なんと、NginxとUnicorn間で/tmpを共有できないとな。

試しにshared/tmpに置いてみたらあっさり動いた。


後日またエラーになってて、socketファイルをみたら775になってた。(のでnginxユーザーからアクセスできなかった)
777にしたら動いたけど、原因不明。

Ansibleで

- name: shared
  file: path=/var/www/{{ item }}/shared state=directory owner={{ user }} group={{ user }} mode=0775 recurse=yes

をやってたせいだった。

Railsのpartial遅い問題

よくRailsのパフォーマンスの話になると槍玉に挙げられるpartial。
ちゃんと自分で確かめたことがなかったので、単純なlink_topartial化して比較してみた。

http://my-rails-bench.bornneet.com/partials
確かに遅い…。
(異常値とか考慮せず単純に時間測っただけだけど、何度かやっても変わらなかったので間違ってないはず)

500回繰り返してるけど、例えば100件のItemモデルを表示するviewで、items/_itemからさらに5つぐらいrenderしたら行くので、意識してないとやっちゃう数字だと思う。

自分が書く時はもちろん、コードレビューとかでもちゃんと意識して見るようにしよう。

参考

ActiveSupportのHash#sliceを知らなかった

http://api.rubyonrails.org/classes/Hash.html#method-i-slice

{ a: 1, b: 2, c: 3, d: 4 }.slice(:a, :b)
# => {:a=>1, :b=>2}

便利だ。
どんどんActiveSupport無しでは生きられなくなって行く。

apipie-rails

https://github.com/Apipie/apipie-rails

APIドキュメントを簡単に作成できるgem。
例えば、https://secure.freee.co.jp/developers/api/doc がこれで作られてると思われる。

この前はじめて使ったんだけど、Examples Recordingがめっちゃ便利だった。
https://github.com/Apipie/apipie-rails#examples-recording

describe "This is the correct path" do
  it "some test", :show_in_doc do
  end
end

RSpec.configure do |config|
  config.filter_run :show_in_doc => true if ENV['APIPIE_RECORD']
end

$ APIPIE_RECORD=examples bundle exec rspec

こんな感じでやれば、テスト結果をサンプルとしてドキュメント内に表示してくれる。
なお、jbuilderを使ってる場合は、render_viewsが必要。これもちゃんとREADMEに書いてある。

便利な世の中だ、、、


Unable to autoload constant Concerns::Foo

https://github.com/Apipie/apipie-rails/issues/347

config/initializers/apipie.rb
config.api_controllers_matcher = "#{Rails.root}/app/controllers/api/**/*.rb" # api以下に絞る

でひとまず逃げた。

Sucker Punchを知らなかった

https://github.com/brandonhilkert/sucker_punch

Railsの他にWorkerを立ち上げずに非同期処理ができる。

リトライとか、指定時間にとか、キューがいるようなのは無理だけど、「コントローラーからキックしたいが、ちょっと重いし、ユーザーへのレスポンスには関係ない」みたいな、ちょっとした処理はこれで十分っぽい。

早速実践投入したけど、超便利。