掲示板 その3 - CGI(Perl)の基本と掲示板作成
目次
掲示板 その3
さらに掲示板に機能を拡張して行きます。今回新たに行なうこと
- 複数行のメッセージ
- タイトル・e-mail欄の追加
- サブルーチンの使用
プログラム
以下のプログラムをテキストエディタで入力してください。
#!/usr/bin/perl
# 掲示板 その3
require "cgi-lib.pl";
print "Content-type: text/html; charset=Shift_JIS\n\n";
# フォーム部分を表示する
print <<EOL;
<html>
<body>
<h2>掲示板</h2>
<form method="post" action="bbs3.cgi">
<table>
<tr>
<th>タイトル</th>
<td><input type="text" name="title" size="40"></td>
</tr>
<tr>
<th>メッセージ</th>
<td><textarea name="message" cols="60" rows="5"></textarea></td>
</tr>
<tr>
<th>お名前</th>
<td><input type="text" name="namae" size="30"></td>
</tr>
<tr>
<th>e-mail</th>
<td><input type="text" name="mail" size="30"></td>
</tr>
<tr>
<th> </th>
<td><input type="submit" value="送信"></td>
</tr>
</table>
</form>
<hr>
EOL
&ReadParse(*form);
# フォームの値を取得
$namae = $form{"namae"};
$mail = $form{"mail"};
$title = $form{"title"};
$message = $form{"message"};
# ログファイル読み込み
open(IN, "bbs3.txt");
@log = <IN>;
close(IN);
# メッセージが入力されているときは書き込み処理を行なう
if ($message ne "") {
# タグの無効化
&deltag($namae);
&deltag($mail);
&deltag($title);
&deltag($message);
# 改行を<br>に変換
$message =~ s/\r\n/<br>/g; # Windows系(\r\n)
$message =~ s/\r/<br>/g; # Mac系(\r)
$message =~ s/\n/<br>/g; # UNIX系(\n)
# ログ先頭に書き込み内容を格納
unshift @log, "$namae\t$mail\t$title\t$message\n";
# ログファイルにロックをかけて書き込み
open(OUT, "+< bbs3.txt");
flock(OUT, 2);
truncate(OUT, 0);
seek(OUT, 0, 0);
print OUT @log;
close(OUT);
}
# ログ表示
foreach $data (@log) {
chop $data;
($namae, $mail, $title, $message) = split(/\t/, $data);
print $title;
print " 投稿者:";
if ($mail ne "") {print "<a href='mailto:$mail'>";}
print $namae;
if ($mail ne "") {print "</a>";}
print "<br><br>\n";
print "$message<br>\n";
print "<hr>\n";
}
print "</body>\n</html>\n";
# タグを除去するサブルーチン
sub deltag {
$_[0] =~ s/</</g;
$_[0] =~ s/>/>/g;
}
入力が終わったら、「bbs3.cgi」という名前でサーバにアップロードし、パーミッションを755にしてください。さらに空のログファイル「bbs3.txt」をサーバにアップロードし、パーミッションを666(読み書き可能)にしてください。その後bbs3.cgiが動くかブラウザで確認してください。
プログラムの説明
今回はテーブルを使ってレイアウトを整えています。フォームの新しい項目として、タイトル、e-mailが増えています。
<td><textarea name="message" cols="60" rows="5"></textarea></td>
複数行のテキスト入力フィールドを表示している部分です。他のフォーム部品とは違い、閉じタグが必要なので注意してください。cols属性は幅、rows属性は高さを文字数で指定します。
# タグの無効化
&deltag($namae);
&deltag($mail);
&deltag($title);
&deltag($message);
名前・e-mail・タイトル・メッセージそれぞれの文字列のタグを無効化している部分です。このように同じ処理を何度もしなければならないときは「サブルーチン」を使います。「deltag」がサブルーチン名、カッコ内は引数と言います。サブルーチン本体の書式は以下のようになります。
sub サブルーチン名 {処理}
上記プログラムでは最下部にサブルーチン本体があります。
# タグを除去するサブルーチン
sub deltag {
$_[0] =~ s/</</g;
$_[0] =~ s/>/>/g;
}
この部分です。$_[0]はサブルーチン呼び出しからの引数が入ります。
&deltag($namae);
この部分を例に説明すると、まず$namaeを引数としてdeltagサブルーチンが呼び出されます。呼び出された側ではまず変数$_[0]に$namaeが入り、$_[0]のタグを無効化しています。結果として$namaeのタグが無効化されることになります。
# 改行を<br>に変換
$message =~ s/\r\n/<br>/g; # Windows系(\r\n)
$message =~ s/\r/<br>/g; # Mac系(\r)
$message =~ s/\n/<br>/g; # UNIX系(\n)
フォームから<textarea>タグで複数行の文字列を送った場合、改行したところには改行を表わす文字コードが入りますが、それをHTMLで表示しても改行されませんので、改行を表わす<br>タグに変換している部分です。ただし、改行を表わす文字コードはコンピュータの種類によってまちまちになります。Windows系は\r\n、Macintosh系は\r、UNIX系(Linuxなど)は\nという改行コードになるので、どの改行コードが来ても<br>に変換できるように処理を行なっています。
# ログ先頭に書き込み内容を格納
unshift @log, "$namae\t$mail\t$title\t$message\n";
名前・e-mail・タイトル・メッセージの4つの項目をタブ区切りで配列先頭に格納しています。
($namae, $mail, $title, $message) = split(/\t/, $data);
タブ区切りで格納されたデータから各項目を取り出しています。
if ($mail ne "") {print "<a href='mailto:$mail'>";}
print $namae;
if ($mail ne "") {print "</a>";}
e-mailが書かれたときのみ名前にメールへのリンク(mailto:)を追加しています。