CGIを使うとWebサーバー内のプログラムの処理結果を返すことができます。これにより、ブラウザに(サーバー内の)プログラムの結果に応じて変化する動的な内容を表示することができます。CGIを実現するためのサーバー側のプログラムはPerlなどの言語を使います。CGIを使うにはWebサーバーの設定で、CGIを使えるように設定する必要があります。
簡単なCGIプログラム
リクエストメソッド
Apache HTTP Server Project
ここでは極めて簡単なCGIプログラムとそれを利用するHTMLドキュメントの例を紹介したいと思います。以下はこのCGIプログラムを使うHTMLのフォーム部分のコードです。
<form action="books.cgi" method="POST">
<br>
<select name="request">
<option value="GET_NUM">GET_NUM</option>
<option value="GET_RECORD">GET_RECORD</option>
</select>
<br>
Offset <input type="number" name="offset" value=0 min=0><br>
Size <input type="number" name="size" value=1 min=1><br>
<input type="reset">
<input type="submit" value="送信">
</form>
formタグのaction属性でこのフォームを処理するCGIプログラムbooks.cgiを指定しています。同じくformタグのmethod属性でサーバーへの送信方法としてPOSTメソッドを指定しています。このフォームにはrequestという名前のセレクトボックスとOffsetとSizeという名前の2つの数値入力フィールドと送信ボタンとリセットボタンがあります。送信ボタンを押すと、フォームの内容がサーバー経由でCGIプログラムに送られます。
以下はPerlで書いたCGIプログラムのソースです。
#!perl
#リクエストメソッドを調べる
my $method = $ENV{'REQUEST_METHOD'};
#フォームのデータを取得
my $query;
if ( $method eq 'GET' )
{
$query = $ENV{ 'QUERY_STRING' };
}
elsif ( $method eq 'POST')
{
read( STDIN, $query, $ENV{ 'CONTENT_LENGTH' } );
}
my @query_ = split(/&/, $query );
my @options;
my $key;
my $val;
foreach ( @query_ )
{
( $key, $val ) = split( /=/, $_ );
$options{ $key } = $val;
}
print "Content-Type: text/html\n\n";
print "<html>\n";
print "<head>\n";
print "</head>\n";
print "<body>\n";
print "[METHOD] $method<br>\n";
print "[QUERY] $query<br>\n";
print "[request] $options{ 'request' }<br>\n";
print "[offset] $options{ 'offset' }<br>\n";
print "[size] $options{ 'size' }<br>\n";
print "</body></html>\n";
exit 0;
このCGIは受け取ったデータを解析して表示するだけの簡単なものです。CGIプログラムへのデータの送信方法は環境変数REQUEST_METHODに書かれています。3行目はこの環境変数の内容を変数$methodに読み込みます。上記のHTMLではPOSTメソッドでフォームを送信しますが、このCGIプログラムがGETメソッドとPOSTメソッドの両方に対応しています。
フォームをCGIプログラムに送る方法はリクエストメソッドによって異なります。10行目はGETメソッドで送られたデータを取り込んでいます。GETメソッドではデータは環境変数QUERY_STRINGによってCGIプログラムに届けられます。14行目はPOSTメソッドで送られたデータを取り込みます。POSTメソッドでは環境変数CONTENT_LENGTHにデータ長が渡され、データ本体は標準入力を使って渡されます。
CGIに届けられるフォームのデータは、次のようにkey=varの組みを"&"で連結した形式になっています。それぞれれのke=vaの組みがフォームの部品の名前(name)と値(value)に対応します。
request=GET_NUM&offset=0&size=1
17行目は送られてきたデータを「&」を区切り文字として分解することで、key=varの組みの配列に変換します。21行目から25行目は配列中のそれぞれのkey=varの組みを”=”を区切り文字として分解して連想配列を作ります。こうすることで、keyの名前からその値を調べることができます。
CGIプログラムは最終的にブラウザに何らかのレスポンスを返します。通常はHTMLドキュメントを返すことが多いようです。HTMLドキュメントを返す場合、
まず最初に(HTMLドキュメントより先に)「Content-Type: text/html」というヘッダーを出力する必要があります。これはCGIからブラウザに返されるデータがHTMLであることを示しています。ここでいう「ヘッダー」とはHTMLのヘッダーではなく、CGIがブラウザに返すデータのヘッダーです。データ本体(HTML)はこの後に続きますが、ヘッダとデータ本体の間には空白行が必要となります。ヘッダの出力と空白行の出力は27行目で行っています(二つの改行があるのはそのためです)。
28行目から38行目はレスポンスデータの本体としてHTMLドキュメントを出力します。
HTMLドキュメントからCGIにデータを送る場合、HTMLのformタグのmethod属性を使って「GET」や「POST」のようなCGIへのデータの送信方法を指定する必要があります。これは「リクエストメソッド」と呼ばれます。
<form action="books.cgi" method="GET">
リンクメソッドには以下のような種類があります。CGIでは通常、GETまたはPOSTメソッドを使います。
GET | GETメソッドの場合、HTMLからサーバーに送られたデータは環境変数QUERY_STRINGを使ってCGIプログラムに渡されます。
環境変数の大きさには制約があるため、この方法は大量のデータをCGIに送る場合には不向きです。このような場合にはPOSTメソッドを使います。 |
POST | POSTメソッドは大量のデータをCGIに送る場合に有利な方法です。POSTメソッドではHTMLからサーバーに送られたデータの長さが環境変数CONTENT_LENGTHを使ってCGIプログラムに渡されます。データの本体はCGIプログラムの標準入力を使って渡されます。 |
HEAD | HEADメソッドはCGIプログラムがレスポンスを返す際にHTTPヘッダのみを返しボディを返しません。ボディを返さない点を除けばGETと同じ動作をします。 |
PUT | サーバーにファイルを転送するために用いられるメソッドです。 |
DELETE | サーバー上のリソースを削除するために用いられるメソッドです。 |
OPTIONS | 利用可能な通信オプションの問い合わせに用いられるメソッドです。 |
TRACE | ループバック用のメソッドです。 |
CONNECT | プロクシへのトンネル接続要求のためのメソッドです。 |
PATCH | リクエストメソッドの種類は、環境変数REQUEST_METHODを使ってCGIプログラムに渡されます。 |