今回はゲスブを作ろう!という事ですが、一番下に置いてある突込みフォームと同じような簡単な物を目標とします。
まず、PHPの特徴としてらformから送られた値を簡単に受け取ることができます。
下のフォームサンプルをご覧下さい
echo '$mes = '.$_POST[mes]; ?>
何か入力してボタンを押してみて下さい。$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>
echo "\$com = $_POST[com]"; ?>
複数行を入力してみてください。一行で表示されますよね?ソースを見るとわかりますが実際には改行コードを送っているので、改行コードを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の前で実行しなければいけません。
$logfile="tt5";include("short.php");?> |