http://www.machu.jp/diary/20060223.html#p02
本文については、大体その通りなので省略。
本文とはちょっと関係のないところで、ゴチャゴチャ書いてたが、なんか、どうでもよくなったので消す。
要点だけ箇条書きで残しとく。

  • apacheの仕様としては、実は、Locationヘッダの値は、scheme名から始まるurlではなく、slashで始まる絶対path指定でも構わない(出力はHTTP/1.1準拠となる)。
    • しかし、その場合、apache独自の挙動(後述)により、本文で言われている、二重投稿防止の効果は得られなくなる。
    • apache独自の挙動というのは、具体的には、Locationヘッダの値がslashで始まる絶対pathだった場合、一旦HTTPクライアントにレスポンスを返すのは保留し、ローカルのリダイレクト先から返すべきコンテンツを先読みして、そっちをHTTPクライアントに返してしまう、という挙動をする。
      • 要するに、CGIスクリプトから見ると、一見リダイレクトされているように見えるが、HTTPクライアントから見ると、リダイレクトされずに直接結果コンテンツが返ってきているように見える(ので、期待されている二重投稿防止効果は得られない)。
  • ステータスコード303等の、HTTP/1.1準拠だがHTTP/1.0準拠ではなく、ブラウザが対応してるかどうか怪しいステータスコードを返す場合は、コンテンツボディとして、中にアンカータグでリダイレクト先や説明文を書いたtext/htmlなドキュメントも一緒にして返せば、一応、対応した事になる(ブラウザ側は1-clickの手間が増えるが)。
    • Locationヘッダ指定時に(自動的に)使われるステータスコード302でも、実は同じだが、apacheが自動的にコンテンツボディ等を用意してくれる為、CGIスクリプト側は普段は意識せずに済むだけ。
    • この場合も当然、非対応ブラウザではリダイレクトはされないので、二重投稿防止の効果は得られない。


まあ、本文で言われてる通り、「Location時は常にscheme名で始まるurlを指定する」「ステータスコード303等のHTTP/1.0準拠でないステータスコードは、対応してないブラウザがあるかも知れないから使わない」で間違いは無いし、その方が分かりやすいが、真実は微妙に違う事もある、という事で。

  • CGIスクリプトが返すべきなのは、HTTP/1.1(1.0)準拠のレスポンスである必要はなく、CGI/1.1準拠のレスポンスで、実際にそこからHTTPクライアントに送られる内容は微妙に違う可能性がある、という事。
    • 普段は意識せずに済むが、実際は、間に何か(mod_cgiが)入ってるからな……。nphモードでない限り。