Lib/site.py

コメントでocean-cityタンに教えてもらった Lib/site.py を見ていたところ、class Quitter(object) という定義が setquit() の中にあるじゃないか(たぶん227行目)。

class Quitter(object):

しかも __call__内で思いっきり標準入力を閉じている。

sys.stdin.close()

理由と思われる但し書きが書いてある。

# Shells like IDLE catch the SystemExit, but listen when their
# stdin wrapper is closed.

『IDLEのようなシェルはSystemExitをキャッチするが、そいつの stdin ラッパーを閉じる時にリッスンしたまんま・・・』わからん。時制あってるのか、これ?

まぁ site.py に関してはドキュメントの 26.11 site -- Site-specific configuration hook を読んだ方が早いかもしれない。

元の話に戻って(もう書くのが嫌になってきたので)ここでは以下のような細工を加えておいた。site.py に main関数(たぶん394行目)があるが、内容とやっていることは以下の通り。

setencoding() ← 中で変数encodingに'ASCII'をセット
execsitecustomize() ← 中でsitecustomizeをimport
(略)
if hasattr(sys, "setdefaultencoding"): ← 貴重なsetdefaultencodingを削除している!
        del sys.setdefaultencoding

http://lowlife.jp/nobonobo/zine/5/6.html の真ん中あたりにも言及があるみたいに、sitecustomize.py というファイルをPYTHONPATHの通っている所に作る。そして中に以下のような記述をしておく。

import sys
sys.setdefaultencoding("shift_jis")

site.pyのsetencoding関数の中に、「テストしたい人は書き換えてくんろ」みたいなことが書いてあるので、そっちを書き換えてもいいかもしれない。

結果、以下のようなコードを実行すると、

# -*- coding: utf-8 -*-
raise IndexError, u"いきなりエラー"

こうなった。

Traceback (most recent call last):
  File "C:\test.py", line 2, in 
    raise IndexError, u"縺・″縺ェ繧翫お繝ゥ繝シ"
IndexError: いきなりエラー

ありがとうocean-city