Wikiエンジンの開発

13.3 CGIの処理


さて本日は"runCGI"関数です。
これはなかなかヘビーな関数です。
いつものようにのんびり見ていこう。
まずは定義です。

runCGI :: (HTTPRequest -> IO HTTPResponse) -> IO ()
runCGI f = do hSetBinaryMode stdin True
              hSetBinaryMode stdout True
              input <- getContents
              env <- cgiEnvs
              res <- f (parseCGIRequest env input)
              putStr (show res)


なんとなくの予想。
まずは、標準入力と標準出力をバイナリモードに設定します。
その上で、標準入力から情報を読み取り、環境変数とともに引数の関数に渡します。
そして最後に、その結果を標準出力に出力する。


では細かく見ていきましょう。
まずはこの部分。

do hSetBinaryMode stdin True
   hSetBinaryMode stdout True


これは次と同じです。

(hSetBinaryMode stdin True) >>= (hSetBinaryMode stdout True)


あれれ?"hSetBinaryMode"関数ってどこに定義されているんだろう?
ここを探してもありませんでした。
型はこんな感じ。

Prelude> :m + System.IO
Prelude System.IO> :i hSetBinaryMode
hSetBinaryMode :: Handle -> Bool -> IO () 	-- Defined in GHC.Handle


う〜ん、ここにはGHC.Handleモジュールがないですね。
定義そのものではありませんが、ここに説明がありました。
抜粋します。

Select binary mode (True) or text mode (False) on a open handle.


まぁ、そういうことなんでしょうね。
stdin、stdoutはあらかじめopenされているので、"a open handle"になるんだと思います。
環境に依存した実装になるので、定義はないのかな?
そして次です。

input <- getContents


これはもうお馴染みですね。
標準入力からデータを読み込むアクションです。
※getContentsの中身(primGetContents)も謎ですけど。


今日はここまで!
明日は"cgiEnvs"関数に入ります。