Permalink
Switch branches/tags
Nothing to show
Find file Copy path
6373171 Feb 17, 2015
1 contributor

Users who have contributed to this file

148 lines (104 sloc) 5.63 KB

unicorn.conf

実質 isucon2 のデフォから変更なし、という結果になった。

listen のオプション. cf. http://unicorn.bogomips.org/Unicorn/Configurator.html#method-i-listen

  • :backlog => number of clients

  • :rcvbuf => bytes, :sndbuf => bytes

    • Linux 2.4+ have intelligent auto-tuning mechanisms and there is no need to specify them
  • :tcp_no_delay => true or false

    • write時にos/kernelレベルでbufferingしてたまってからsendするのをやめて即座にsendします.
    • 小さいパケットはまとめて、それからwriteするようにしましょう.
    • cf. kazeburo yapc 2013 http://www.slideshare.net/kazeburo/yapc2013psgi-plack
  • :tcp_nopush => true or false

  • :tries => seconds

    • Times to retry binding a socket if it is already in use. Default 5 seconds.
  • :delays => seconds

    • Seconds to wait between successive tries. Default: 0.5 seconds
  • :tcp_defer_accept => integer

    • Default 1. コネクションが完了したタイミングではなくデータが到着した段階でプロセスを起こします.
    • プリフォーク型のhttpdにおいて処理中となるプロセス数を減らすテクニック
    • cf.kazeburo yapc 2013http://www.slideshare.net/kazeburo/yapc2013psgi-plack

unicorn.conf

@dir = "/home/isucon/webapp/ruby/"
working_directory @dir

worker_processes 8 # CPUの数 * 2 ぐらい?
# unicornはノンブロッキングじゃないのでI/Oが詰まるような状況においてはCPUのコア数より増やしたほうが効率が良い.
# メモリが許す限り増やす。どこかで頭打ちにはなると思うが

# listen "/dev/shm/app.sock", backlog: 8192 # unix domain socket 版. パスは nginx と合わせること
listen "0.0.0.0:5000", tcp_nopush: true, tcp_defer_accept: 1 # 安全というかデフォ
# listen "0.0.0.0:5000", tcp_nopush: true, tcp_defer_accept: 1, tcp_no_delay: true # アプリの実装を気を付ける必要あり

pid File.join(@dir, "tmp/pids/unicorn.pid")
timeout 60 # default: 60
# stderr_path File.join(@dir, "log/unicorn.stderr.log")
# stdout_path File.join(@dir, "log/unicorn.stdout.log")

preload_app true # allow copy-on-write-friendly GC to save memory
# http://rubyenterpriseedition.com/faq.html#adapt_apps_for_cow (for REE, probably not necessary)
GC.respond_to?(:copy_on_write_friendly=) and GC.copy_on_write_friendly = true

# 例えば、GC を止める(特に速くならなかった)
# after_fork do |server, worker|
#   GC.disable
# end

# Below is for ActiveRecord
=begin
before_fork do |server, worker|
  defined?(ActiveRecord::Base) and ActiveRecord::Base.connection.disconnect!
  old_pid = "#{server.config[:pid]}.oldbin"
  if old_pid != server.pid
    begin
      sig = (worker.nr + 1) >= server.worker_processes ? :QUIT : :TTOU
      Process.kill(sig, File.read(old_pid).to_i)
    rescue Errno::ENOENT, Errno::ESRCH
    end
  end
  sleep 1
end

after_fork do |server, worker|
  defined?(ActiveRecord::Base) and ActiveRecord::Base.establish_connection
end
=end

例えばGCを止める

特に速くならなかったので不要。

設定

unicorn.conf の最後 or after_fork ブロックに追加

after_fork do |server, worker|
  GC.disable
end

Gemfile

gem 'unicorn-worker-killer' # https://github.com/kzk/unicorn-worker-killer

configu.ru

require 'unicorn/oob_gc'
use Unicorn::OobGC, 10 # run GC each 10 requests

require 'unicorn/worker_killer'
# Max Requests per Worker
use Unicorn::WorkerKiller::MaxRequests, 3072, 4096
# Max Memory size (RSS) per worker
use Unicorn::WorkerKiller::Oom, (192*(1024**2)), (256*(1024**2))

尚、OobGC の値を大きく(100とか)すると、

09:01:25 web.1  | Mysql2::Error - Can't create a new thread (errno 11); if you are not out of available memory, you can consult the manual for a possible OS-dependent bug:
09:01:25 web.1  |       /home/game/.rbenv/versions/2.0.0-p247/lib/ruby/gems/2.0.0/gems/mysql2-0.3.11/lib/mysql2/client.rb:44:in `connect'
09:01:25 web.1  |       /home/game/.rbenv/versions/2.0.0-p247/lib/ruby/gems/2.0.0/gems/mysql2-0.3.11/lib/mysql2/client.rb:44:in `initialize'

とエラーが出た。Unicorn::WorkerKiller::Oom で調節 .... 難しい。ちょこちょこ Mysql2::Error が出る。 やはり Unicorn::OobGC をそれなりに小さく保たないといけない模様。

worker が死んで mysql に新規に接続しようとするので、コネクションの数が増えるのかな ... 尚、WorkerKiller が発動するとログに以下のように出る。

09:10:08 web.1  | W, [2013-09-30T09:10:08.501329 #9605]  WARN -- : #<Unicorn::HttpServer:0x007ffb31f1a048>: worker (pid: 9605) exceeds memory limit (126382080 bytes > 99290060 bytes)
09:10:08 web.1  | W, [2013-09-30T09:10:08.501476 #9605]  WARN -- : Unicorn::WorkerKiller send SIGQUIT (pid: 9605) alive: 15 sec (trial 1)
09:10:08 web.1  | I, [2013-09-30T09:10:08.538649 #9481]  INFO -- : reaped #<Process::Status: pid 9605 exit 0> worker=29