PHPの勉強として掲示板を作成しているのですが、謎の二重書き込みに出会い躓いています。
下記はテストとして書いた、状況が再現されるソースです。
<?php
$filename = './test.dat';
if($_REQUEST) {
$data = file($filename);
$newdata = "{$_REQUEST['newdata']}\n";
$logfile = @fopen($filename, "r+");
flock($logfile, LOCK_EX);
foreach($data as $value) {
fputs($logfile, $value);
}
fputs($logfile, $newdata);
flock($logfile, LOCK_UN);
fclose($logfile);
}
?>
<html>
<head><title>TEST</title></head>
<body>
<form action="test.php">
<input type="text" name="newdata">
<input type="submit">
</form>
</body>
</html>
5、6行目で
$newdata = "{$_REQUEST['newdata']}\n";
$data[] = $newdata;
とした場合、DATを逆順にして
$newdata = $_REQUEST['newdata'];
$array_unshift = $newdata;
とした場合、また、そこで追加せずに書き込み処理を
$logfile = @fopen($filename, "r+");
while(!feof($logfile)) {
$data[] = fgets($logfile);
}
fputs($logfile,$newdata);
foreach($data as $value) {
fputs($logfile, $value);
}
とした場合、など…どうやってもなぜか同じ症状が出ます。
しかももっと不思議なのは、どこでおかしくなっているのか調べようと思い途中にprint_r($data)を入れると、場所によってはなぜか二重書き込みが起きなかったりするのです。
検索しても同じ状況は見つけられずどうしたものかと悩んでおります。
情報が足りないかもしれませんが、何か気づいた方がいましたら教えてください。よろしくお願いします。
No.3ベストアンサー
- 回答日時:
if($_REQUEST)の所為でページにアクセスした時点でfopen以下の処理が実行されてしまっている→2重処理
(これはログファイルをテキストエディタか何かで開いたまま実行すると確認できます)
入れる場所によっては~の下りはfputsの前後で結果が変わっているのでは?
解決方法はPOSTメソッドに変更するのが手っ取り早いです。
送信されるまで実行されないので2重処理もされません。
<form action="test.php" method="post">
<input type="text" name="newdata">
<input type="submit">
if($_POST) {
$data = file($filename);
$newdata = "{$_POST['newdata']}\n";
if($_REQUEST)やmethod="get"がいけないなんて思いもしませんでした(お恥ずかしい)。『形になるまではパラメータが見えている方が分かりやすい』なんて考えた罰ですね。
>fputsの前後で
まさにそうです。情報を出し忘れていてすみません。
cyanberryさんの場合は偶然だったのかが気になりますが、解決したので締め切らせていただきます。
お三方ありがとうございました。
No.2
- 回答日時:
No1さんの指摘もその通りなのですが、試しにソースそのままをコピペして実行してみたら、別に2重書き込みになりませんでしたよ。
このソースとは違うものが動いてませんか?
この回答への補足
回答ありがとうございます。
試しに新しいディレクトリにこのtest.phpとtest.datだけを入れて実行したのですがやはり二重になりました。
本当に質問文に載せた分しかないファイルでアップロードしているので、何がcyanberryさんと違うのかまったく見当が付きません。
回答いただいたのにすみません。
No.1
- 回答日時:
?
これって追加書き込みしたいんですか?
それとも新規ラインを追加した新しいファイルをつくるんですか?
@fopen($filename, "r+");
は
@fopen($filename, "a");
なのでは?
あと、エラー処理をスキップしているので、受け取りハンドルは厳密にしたほうがいいとおもいます。
今のを整理すると、
先読みの部分は使いません。(必要すらない)
function hoge() {
-> $filename = './test.dat';
-> if($_REQUEST) {
-> -> $logfile = @fopen($filename, "a");
-> -> -> fputs($logfile, $newdata);
-> -> fclose($logfile);
-> }
}
こんだけで全部終わるんですが、だめですか?
この回答への補足
回答ありがとうございます。追加書き込みです。
書き忘れてしまったんですが、"a"とか一度中身を全部配列に入れてから"w"で開いて書き込みとかも実はやりました。やはり二重になってしまいます。
ちなみにもうひとつ書き忘れていたのが、test.phpはこのスクリプト自体ということです。
教えていただいた記述をコピーして実行しましたが、やはり二重になってしまいました。せっかく解答していただいたのにすみません。
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
似たような質問が見つかりました
- PHP PHPでCookieを使った訪問回数について 1 2023/05/28 14:10
- PHP PHPで画像の渡しが上手く行きません。 1 2023/02/02 09:39
- PHP PHPでユーザー情報を入力して簡易ログイン機能をつくってみたのですが 1 2023/05/29 08:51
- PHP 入力した部分を表示させたまま(保持)するにはどうすれば良いでしょうか? 1 2023/01/25 11:14
- Excel(エクセル) PHPプログラムをエクセルに張り付けると検索ボックスがでてくる! 3 2022/05/08 07:10
- CGI htmlからパラメータで、cgiに渡したい。 1 2023/02/06 16:15
- PHP php ログイン 1 2022/11/01 00:24
- PHP htmlspecialcharsが機能していないです。 バグですか? 1 2022/04/05 01:22
- PHP if(preg_match("/[^0-9]/",$gu_d)){意味を教えてください。 1 2022/05/06 05:37
- PHP ここでの ②if($su_d<>"")の比較演算子 を使う理由は 1 2022/03/26 02:33
関連するカテゴリからQ&Aを探す
おすすめ情報
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
PHPとHTML+Xamppの掲示板で画像...
-
PHPで画像の渡しが上手く行きま...
-
複数行のデータ一括更新に関して
-
POSTデータのNAME属性をVALUEに...
-
IEで、フォームにたとえば
-
チェックボックスを用い、MySQL...
-
フォームの途中で追加するには
-
検索時の選択内容を保持する方法
-
PHPでユーザー情報を入力して簡...
-
PHPでCookieを使った訪問回数に...
-
現在ラジオボタンのデータベー...
-
チェックボックスによる検索
-
【PHPチェック】ラジオボタンが...
-
フォームでのリセットを使う方法
-
phpやmysqlで作る簡易掲示板作...
-
配列をhiddenで
-
DBの値をチェックボックスに反...
-
チェックボックスから複数のval...
-
PHP+MySQLで複数のラジオボタン...
-
HTMLで前の画面に戻る時、入力...
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
<input type="hidden" >で配列...
-
HTMLで前の画面に戻る時、入力...
-
PHPでユーザー情報を入力して簡...
-
PHP ボタンが押されたら処理を...
-
PHPとHTML+Xamppの掲示板で画像...
-
syntax error, unexpected '}' ...
-
検索時の選択内容を保持する方法
-
PHPでCookieを使った訪問回数に...
-
チェックボックスによる検索
-
フォームでのリセットを使う方法
-
PHPで画像の渡しが上手く行きま...
-
チェックボックスによる検索(...
-
フォームへの前回入力値をクリ...
-
フォームボタンを押すたびに数...
-
php mysql でチェックボックス...
-
PHPの関数実行
-
phpで分からないエラーが出てし...
-
PHPで、ボタンを押すと同じペー...
-
ラジオボタンをsessionで使いたい
-
入力フォーム→確認画面→送信画...
おすすめ情報