CORESERVER で web.py を CGI として動かす

タイトルまんま。 CORESERVER で Python のフレームワーク web.py を動かしました。

1. web.py のインストール

注意

僕の環境では以前のエントリ CORESERVER で Python 2.7.1 を動かした のように、 Python 2.7 をインストールしてあり、 easy_install が使えます。 そのため、インストールに easy_install を使ってしまっています。

これができない人は、 web.py のサイトからファイルをダウンロードしてきて、設置、 PYTHONPATHの挙動を正確に把握する - ぎじゅっやさんなどを参考に、パスを通してあげればいいと思います。

xxx@yyy:~> easy_install web.py

xxx@yyy:~> python
>>> import web
##エラーがでなければ成功

2. wsgi.py を編集

web.py は WSGI 上で動き、 WSGI では内部でマルチスレッド処理をしていますが、 CORESERVER ではマルチスレッド処理は禁止 ( のはず ) ですので、マルチスレッド処理を無効にするために web.py モジュールの中の wsgi.py を編集してやります。

xxx@yyy:~> vim ~/local/lib/python2.7/site-packages/web.py-0.35-py2.7.egg/web/wsgi.py
#17行目の
    return flups.WSGIServer(func, multiplexed=True, bindAddress=addr, debug=False).run()
#を
    return flups.WSGIServer(func, multiplexed=True, bindAddress=addr, debug=False, maxSpare=0).run()
#と変更する
これでマルチスレッドを無効化

3. wsgi.py 内で PATH_INFO を書き換える

web.py では全てのリクエストを一手に一つのスクリプトが受け、リクエスト URI がそのスクリプト内に登録された URI のパターンにマッチする場合、それに対応するクラスで処理してやるのですが、 PATH_INFO を書き換えてやらないと正常にマッチしません。 そのため、 PATH_INFO を書き換えてやり正常なマッチングができるようにします。

# xxx@yyy:~> vim ~/local/lib/python2.7/site-packages/web.py-0.35-py2.7.egg/web/wsgi.py
#31行目に以下の6行を追加してやる
    path_begin = os.environ['SCRIPT_NAME'].rfind('/')
    try:
        query_begin = os.environ['REQUEST_URI'].index('?')
        os.environ['PATH_INFO'] = os.environ['REQUEST_URI'][path_begin:query_begin]
    except ValueError:
        os.environ['PATH_INFO'] = os.environ['REQUEST_URI'][path_begin:]

4. index.py を書く

いよいよ、実際にページを表示するスクリプトを書いてやる。 他のモジュールに依存しない、単純に web.py だけを使うスクリプト。 index.py って名前で保存してやった。

#!/virual/xxx/local/bin/python
#-*-coding: utf-8-*-

import web

urls = (
    '/hoge', 'hoge',
    '/', 'index',
    '', 'index',
)

app = web.application(urls, globals())

class index:
    def GET(self):
        return "Hello world"
class hoge:
  def GET(self):
    return 'HOGEHOGE'

if __name__ == "__main__":
    app.run()

5. mod_rewrite 使って全てのリクエストを index.py に転送してやる

「3. wsgi.py 内で PATH_INFO を書き換える」で言及したように、全てのリクエストを転送してやるため .htaccess に次を記述

RewriteEngine on
RewriteBase /
RewriteRule .* index.py [QSA]

6. 動作確認

そいじゃ実際に動作確認。 hoge.com で動かしてるとすると、 hoge.com にアクセスで Hello World が表示され、 hoge.com/hoge にアクセスで HOGEHOGE が表示されれば成功

最後に

分かりにくい表現でゴメンナサイ。