読者です 読者をやめる 読者になる 読者になる

自作したサーバープログラムをCircusで動かす

Python Ruby Circus

Circusからファイルディスクリプタが渡されるのでsocket.fromfdを使えばいいらしい。

Python

Pythonのバージョンは2.7.2。

myserver.py
# coding: utf-8
import sys
import socket
import logging
import select

content = """HTTP/1.0 200 OK
Content-Type: text/plain
Length: 13

Hello world!
"""
content_length = len(content)


def main():
    sock = socket.fromfd(int(sys.argv[1]), socket.AF_INET, socket.SOCK_STREAM)
    try:
        while True:
            ready, notused, notused = select.select([sock.fileno()], [], [], 30)
            if ready[0] == sock.fileno():
                conn, addr = sock.accept()
                data = conn.recv(1024)
                conn.send(content, content_length)
                conn.close()
    except KeyboardInterrupt:
        sys.exit(0)


if __name__ == '__main__':
    main()
myserver.ini

myserver.pyを使うCircusの設定ファイル。

[circus]
check_delay = 5
endpoint = tcp://127.0.0.1:5555

[watcher:hello]
cmd = python -u myserver.py $(circus.sockets.web)
use_sockets = True
numprocesses = 5

[socket:web]
host = 0.0.0.0
port = 8000
実行
$ circusd myserver.ini

curlで叩く。

$ curl http://127.0.0.1:8000/
Hello world!

Ruby

で、Python以外で作ったサーバーでも大丈夫か試すってことでRubyで同じようなものを書いた。
Rubyのバージョンは1.9.1。

myserver.rb
require 'socket'

CONTENTS = <<EOS
HTTP/1.0 200 OK
Content-Type: text/plain
Length: 13

Hello world!
EOS

sock = Socket.for_fd(ARGV[0].to_i)
while true
  ready = IO::select([sock])
  ready[0].each do |serv|
    conn, addr = serv.accept
    conn.recv(1024)
    conn.write(CONTENTS)
    conn.close
  end
end
myserver2.ini
[circus]
check_delay = 5
endpoint = tcp://127.0.0.1:5555

[watcher:hello]
cmd = ruby myserver.rb $(circus.sockets.web)
use_sockets = True
numprocesses = 5

[socket:web]
host = 0.0.0.0
port = 8000
実行
$ circusd myserver2.ini

curlで叩く。

$ curl http://127.0.0.1:8000/
Hello world!

いいね!