たとえば次のようなフォームを作ってみましょう。
<title>フォームのテスト</title> <h1>フォームのテスト</h1> <form action="test.cgi" method="post"> <p>メッセージ: <input name="message" size=60> </form>
このフォームに書き込むと test.cgi というCGIが起動します。これはたとえば次のように作っておきます。
#include <iostream> #include <string> using namespace std; int main() { string s; cin >> s; cout << "Content-type: text/html\n\n"; cout << s << endl; }
これでたとえば「Hello」と打ち込むと,
message=Helloと返ります。
メッセージの頭に「message= という余分な部分が付きましたね。 これは
<input name="message" ...>と指定したからです。 この部分を削るには substr() という関数を使います。 たとえば上の s を s.substr(8) にすると,最初から8文字を削ってくれます。
上のフォームは日本語を入力すると変になりますね。 次のように関数を使って変換します。
#include <iostream> #include <string> using namespace std; string decode(const string& s) { string t; string::const_iterator p = s.begin(); while (p != s.end()) { if (*p == '%') { if (++p == s.end()) break; int d = *p; if (++p == s.end()) break; int e = *p; d = (d >= 'A') ? (d & 0xdf) - 'A' + 10 : d - '0'; e = (e >= 'A') ? (e & 0xdf) - 'A' + 10 : e - '0'; if (d >= 0 && d < 16 && e >= 0 && e < 16) t += char(16 * d + e); } else if (*p == '+') { t += ' '; } else if (*p == '&') { t += '\n'; } else { t += *p; } p++; } return t; } int main() { string s; cin >> s; s = decode(s); cout << "Content-type: text/html\n\n"; cout << s.substr(8) << endl; }
書き込んだ内容をファイルに追加(アペンド) していけばチャットや掲示板になります。
たとえば上の「フォームのテスト」のファイル名が formtest.html だったとすると,次のような CGI にすれば,formtest.html に書き込んだ内容がどんどんアペンドされていきます。
int main() { string s; cin >> s; cout << "Content-type: text/html\n\n"; ofstream out("formtest.html", ios_base::app); out << "<p>" << decode(s).substr(8) << endl; cout << "<p>書き込みました\n"; }
「書き込みました」の下に「戻る」リンクを付けてみましょう。 あるいは自動的に戻るようにするにはどうしたらいいでしょうか (ヒントは ここ)。
★もっと本格的なチャットプログラムの C++ ソースと解説は ここ にあります。 掲示板の C++ ソースと解説は ここ にあります。
アンケートやクイズを作ってみましょう。
<form action="test.cgi" method="post"> <p>性別: <input type="radio" name="1" value="M">男 <input type="radio" name="1" value="F">女 <p>趣味: <input type="radio" name="2" value="1">遊び <input type="radio" name="2" value="2">勉強 <input type="radio" name="2" value="3">なし <input type="submit" value="送る"> <input type="reset" value="クリア"> </form>
test.cgi はこのページの最初のもの(decode() を使っていないもの)をとりあえず使ってみましょう。 たとえば「女」「遊び」を選ぶと,
1=F&2=1と表示されます。つまり,name= で指定した名前と,value= で指定した値が = で結ばれて送られます。項目の区切りは & になります。
これから特定の場所を切り出すには,s[番号] という使い方をします。 番号 は文字の位置で,0 から始まる番号で数えます。
たとえば次のようにできます。
#include <iostream> #include <string> using namespace std; int main() { string s; cin >> s; cout << "Content-type: text/html\n\n"; if (s[2] == 'M') cout << "<p>あなたは男ですね\n"; else cout << "<p>あなたは女ですね\n"; if (s[6] == '1') cout << "<p>遊びはほどほどにね!\n"; }
リンクはご自由にどうぞ。
松阪大学 奥村晴彦 okumura@matsusaka-u.ac.jp
Last modified: Thu Dec 16 22:47:37 1999