2007-01-27

雑談というか告知というか。

「さくら Python」で改訂したいところ

『さくらのレンタルサーバ』で Python 外部モジュールを使う」が参考になっている方々が少なからずいるようで、書いた者としてはやってよかったと思っています。(べつにページの有用さ具合を測る尺度にはならないけど)はてなブックマークに入れている人もいるし、web.py (作ったのは Aaron Swartz だ)を導入したり、Trac を動かす(!)などの参考文献として参照してもらってるようです。

ただ、そこで書いた user モジュールを使って sys.path をいじる方法を気に入ってしまった人が思いのほか多いようなのが心配になってきた。あのやり方はよくないと思います。

あの節を書いている時点では、なんとなく、直感的に、「これはどうなのか」というサインが頭の片隅に浮かんでいただけの状態で、理論的にそれを説明することには及ばなかったのでそのままタイプを進めてしまったのですが(その感触があったせいで、今の版でもそれほどプッシュはしていない)。その後、考えも整理できてきた今では、はっきりと「これはよくない」と考えています。改訂したら、この箇所は削除するか、ちょっと触れる程度にしたい。

なぜか? CGI に限らず、プログラミングをよくしている人なら当然すぐにそう考えたはずのことなのですが……。文章にすると時間がかかるので(そしてそれをやるならここじゃなくて「さくら Python」の記事でやればいいわけで)、以下思いつくままに箇条書き。

  • プログラム(ここでは CGI スクリプト)を書くときに意識しなければいけないこととして、どこまで可搬性(ポータビリティ)を持たせるか(移植性、といってもいい)、ということがある。
  • 自分しか使わないスクリプトなら、ファイルのパスでもログインパスワードでも、スクリプトにハードコードしてかまわない。
  • しかしこうしたスクリプトはよそで動かす(便利なものは遅かれ早かれそうしたくなる)ときにコードを書き換えなくてはいけない(「さくら Python」の当該節も文脈はそういう流れ)。
  • そこでプログラマは環境に依存しない部分と、状況に応じて変更する必要がある部分とを分ける。前者をモジュールにしたり、後者を設定ファイルにしたりする。
  • 可搬性の境界ははっきりしておいたほうがよい。つまり、「このファイル群は何も考えずによその環境へうつせる」し、よその環境へ移したら「あのファイル群(だけ)を書き換えればよい」という状況にしておくべきだ。
  • つまり環境依存部分は「分ける」のが肝心なので「隠す」のはまったくよくない。
  • sys.path を追加するのはもちろん環境依存のプライベートな話。つまりこれが書いてあるファイルは環境依存のファイルということになる。
  • しかしある CGI スクリプト foo.cgi からそれを追い出して、代わりに import user したところで、foo.cgi に可搬性ができたといえるのか。いえない。なぜなら import user とはプライベートな用途の最たるもので、これはモジュールのパスを追加するための仕組みでもなければ、CGI のための仕組みですらないimport user してるスクリプトというのはプライベートの領域に属するファイルとみなすべき。
  • .pythonrc.py で何が行われるのか、import user している側からは、それは想像もつかない。自前の関数で range をオーバーロードしてるかもしれない。
  • どうせスクリプトがプライベートなままなのなら、sys.path.append(...) と直接書いても移植性は(移植性がないことに)変わりないし、むしろそこで何をすべきかがわかってよい。はじめから「これは環境によって書き換えるファイル」と考えておけば、sys.path が通ってないから云々という問題に悩まされることはかえって少なくなる。
  • ほんとうに foo.cgi に可搬性を持たせたいなら、設定ファイルを作って、それを読み込むようにするべき。これで foo.cgi はポータブルになったけど、総ファイル数は増えている(のでよく考えよう)。

じっさいに改訂したら、こんな理由までこまごまとは書かないと思いますけど、まあ考えの経緯はこんな感じです……。最初に感じてた「どうなのか」サインを、記事を読んだ人も持ってくれるかなあ、というのをあてにしてたということもあったのかもしれない。そもそも import user じたいが暗黙的で Python らしくないですよね。

ここに書いたって読む人はほとんどいないから、一刻も早く改訂しないと……。