5.ゲスブを作ろう〜フォーム処理
フォームから受け取る

今回はゲスブを作ろう!という事ですが、一番下に置いてある突込みフォームと同じような簡単な物を目標とします。

まず、PHPの特徴としてらformから送られた値を簡単に受け取ることができます。
下のフォームサンプルをご覧下さい

<form action="tt5.php" method="POST">
<input type="text" name="mes" size="20">
<input type="submit" value="submit"> </form>

何か入力してボタンを押してみて下さい。$mesの部分に入力文字が表示されましたか?

PHP4.1以前ではフォームのテキストボックスで指定した name="mes" の名前が、そのまま変数名$mesとなって、そこに入力された文字列が入りましたが、
現在のPHPでは、method="POST"の場合$_POST配列に値が入ります。もしname="mes"ならば、値を受け取るには「$_POST['mes']」を参照すればいいです。

GETにて送信した場合は、$_GETに値が入ります。「read.php?bbs=news」などのURLにくっついた変数も$_GETに格納されます。この場合は$_GET['bbs']="news"となります

もちろんテキストボックスだけでなく、チェックボックスやhiddenの値もname="???"とした変数名に受け渡されます。
サンプルをご覧ください。


仕組みを考えよう

ゲスブを作る際の処理の流れを考えましょう。今回はデータの記録にファイルを使います。データベースでもいいですけど、、

処理としては、書き込み処理と表示する処理が必要です。削除は付けません。HTML内にPHPを埋め込む事にします。

ログに書き込むのは一行に一データとします。こうすると配列での処理が楽です。
ファイルフォーマットは、掲示板だと通常カンマや<>で区切って保存しますが、今回は隠したいデータも無く、簡単な物なので 表示する状態にして書き込みます。こうすると表示する際の処理が楽です。


フォームを作ろう

まずは、HTML部分を作成します。フォームの解説はしませんが、いろんなソースから<form>〜</form>部分を参照するといいでしょう。

とりあえず、名前欄とコメント欄を付けたフォームとします。
action=<? echo $PHP_SELF;?> とするとターゲットが自分自身となります。

<form method="post" action="<? echo $PHP_SELF; ?>">
<b>N </b><input name="name" type="text" size="10"> <b>:</b><input name="mes" type="text" size="40">
<input type="submit" value=" Send ">
</form>

表示処理

表示は簡単です。一行に一データ入っているので、最新10件表示させるにはログ先頭から10行読み込めばいいです。

$lines = file("log.log");
for($i = 0; $i < 10; $i++) {
  echo $lines[$i];
}

まず file() 関数でファイルの内容を配列に入れます。ログの一行分(改行まで)が配列の一要素となります。

次にfor文で配列の番号を増やして出力していきます。$lines[0]がファイルの一行目となっています。

ついでにカンマ等で区切った場合も示しておきます。

$lines = file("log.log");
for($i = 0; $i < 10; $i++){
  list($now,$name,$mes)=explode(",",$lines[$i]); 
  echo "$name >> $mes <font size=1>[$now]</font><br>\n";
}

途中まで一緒ですが、explode() 関数によりカンマで分割して、それを list() で変数に代入します。

代入した変数をフォーマットして出力します。

とりあえずここまでを実行してみましょう。適当なログファイルを用意してください。
[ ソース ] [ 実行結果 ][ ログ ]


書き込み処理

書き込み処理を実行するのは、名前とコメントが入力された場合とすると「もし名前とコメントに何か入力されたら」となります。プログラム的に置き換えると「もし変数nameと変数mesに値が入っていたら」となり、次のように書けます

if($name && $mes){
 

次に変数の処理をします。外部からくる値は何が来るかわかりません。HTMLタグを入力されれば荒らされる可能性があるのでHTMLタグを変換しましょう。htmlspecialchars() 関数を使います。タグ除去にはstrip_tags() があります。

$mes = htmlspecialchars ($mes);
$name = htmlspecialchars ($name);

一番↑で「パソコン機能」と入力するとわかりますが、スクリプトをShift-JISで書いた場合「ソ能表」など2バイト目が5Cになっているものは後ろに\マークが付きます。これはphp.iniでmagic quotes gpc がOnになっている為です。

EUCで書けない場合やmagic_quotes_gpcがOffに出来ない場合は\マークを除去します。

if(get_magic_quotes_gpc()){
  $mes = stripslashes($mes);
  $name = stripslashes($name);
}

get_magic_quotes_gpc()は、php.iniの設定を返します。Onなら1です。Onの場合stripslashes() 関数でバックスラッシュを取り除きます。

次に日付けのフォーマットを決めます。gmdateと+9時間で海外の鯖でも日本時間が出ます。

$now = gmdate("d(D) h:i a",time()+60*60*9);

今回はログの中身をそのまま表示するので、HTMLの(実際に表示する)状態でファイルに書き込みます。フォーマットして変数に入れておきましょう。

$dat = "$name >> $mes <font size=1>[$now]</font><br>\n";

データの最後に改行コードを入れます。これでログ一行一データとなります。

ログの書き込みですが、一般に掲示板などでは

・先頭から書き込んで、先頭から表示
・最後に書き込んで、後ろから表示

の2つの方法があると思いますが、今回は前者の方法で行います。
ファイルの先頭に最新データを書き込み、現データを一定件数(100件)を越えないように書き込みます。

$lines = file("log.log");	//いままでのログを配列に読み込む
$fp = fopen("log.log","w");	//ログをオープン(空になる)
fputs($fp,$dat);		//データを書き込む(先頭に)
for($i = 0; $i < 99; $i++)	//いままでの分を追記 
  fputs($fp, $lines[$i]);	//(配列0-98→現ログ1-99行目)
fclose ($fp);

となります。 ログを100件にまとめるには現ログの99件を書き直せばいいです。

さて表示と書き込みをまとめてみましょう。書き込み処理は表示より前に持ってきた方がいいですね。同じ名前(ログファイル名)や後から変更する数値(表示行数)は変数か定数として、先頭に移動させましょう。

[ ソース ] [ 実行結果 ][ ログ ]

効率などはあまり考えてないので、追求したい方は考えてみてください。

最新ログを下に表示するバージョン
[ ソース ] [ 実行結果 ]


複数行の入力

複数行の場合は、やや違った処理が必要となります。TEXTAREAで入力欄を作ってみます。

<form method="post" action="tt5.php">
<textarea name="com" cols="40">
</textarea>
<input type="submit" value="submit"> </form>

複数行を入力してみてください。一行で表示されますよね?ソースを見るとわかりますが実際には改行コードを送っているので、改行コードをHTMLの改行「<br>」に変換すればいいんです。

ただし、改行コードはOSによって異なるので統一する必要があります。 \nに統一してから、<br>に変換します。

$com = $_POST['com']; 	//method="post"なら$_POST、getなら$_GET
$com = str_replace("\r\n", "\r", $com);	//Win系は\r\n
$com = str_replace("\r", "\n", $com);	//Mac系は\r
$com = str_replace("\n", "<br>", $com);	//\n除去して<br>

nl2br()を使えば、改行の前に<br />を入れてくれますが、改行コードは消えません

これで複数行がデータ上一行になり、HTMLで表示した時には複数行となります。

TEXEAREAを使ったサンプルです
[ ソース ] [ 実行結果 ]


クッキーやページ処理については、掲示板スクリプトを参考にして見てください。setcookie() はすべてのHTML文やechoの前で実行しなければいけません。





<<Prev  Next>>


LastModified