Автор Тема: Внесение изменений в текстовый файл  (Прочитано 14620 раз)

0 Пользователей и 1 Гость просматривают эту тему.

Оффлайн UltraMax

  • Завсегдатай
  • Пользователь
  • **
  • Сообщений: 98
  • +0/-0
  • 0
    • Просмотр профиля
    • http://www.dinamo-minsk.org
я использую текстовый файл для хранения инфы
и внесения изменения в него вношу так

тут мне надо чтобы оно файл уменьшило до нуля и влепила измененный текст
    $handle = fopen ("/home/dmnorg/results.txt", "w");
    fwrite($handle, $contents_replaced);
    fclose($handle);

и в другом оно просто добавляет строчку
    $handle = fopen ("/home/dmnorg/results.txt", "a");
    fwrite($handle, $string);
    fclose($handle);

такой вопрос - оно может перезатереть файл при одновременном доступе???
может надо использовать какие-то функции для защиты от одновременного доступа?
или сам php будет отслеживать данный процесс???
в общем вопрос простой - если скрипт открыл файло на запись
и тут второй еще раз лезет его открыть на запись

что тогда?

Оффлайн ThE0ReTiC

  • Главный по тарелочкам
  • Глобальный модератор
  • Ветеран
  • *****
  • Сообщений: 4041
  • +2/-0
  • 2
    • Просмотр профиля
    • http://
Внесение изменений в текстовый файл
« Ответ #1 : 07 Декабря 2004, 23:17:02 »
[p]flock[/p]
AS IS...

Оффлайн UltraMax

  • Завсегдатай
  • Пользователь
  • **
  • Сообщений: 98
  • +0/-0
  • 0
    • Просмотр профиля
    • http://www.dinamo-minsk.org
Внесение изменений в текстовый файл
« Ответ #2 : 08 Декабря 2004, 11:49:54 »
Млять - как и в перле
Но почему же в документации нет ссылки на это
Точнее когда описывается функция fwrite - нет ссылки на flock
зато есть
See also fread(), fopen(), fsockopen(), and popen().
твою бабушку, два раза уже результаты херились :((

Оффлайн UltraMax

  • Завсегдатай
  • Пользователь
  • **
  • Сообщений: 98
  • +0/-0
  • 0
    • Просмотр профиля
    • http://www.dinamo-minsk.org
Внесение изменений в текстовый файл
« Ответ #3 : 08 Декабря 2004, 16:20:21 »
Сейчас используется вот такая конструкция
в одном скрипте вот так открываетс файл
$handle fopen("/home/dmnorg/results.txt""r");
    if (
flock($handleLOCK_SH)) { // do an exclusive lock
    
fwrite($handle$contents_replaced);
    
flock($handleLOCK_UN); // release the lock
    
}

и во втором скрипте вот так
$handle fopen ("/home/dmnorg/results.txt""a");
    if (
flock($handleLOCK_EX)) { // do an exclusive lock
    
fwrite($handle$string);
    
flock($handleLOCK_UN); // release the lock


все равно из файла /home/dmnorg/results.txt
пропадают записи :( С чем это может быть связано?

Не может ли это быть связано с тем, что у меня в одном месте на чтений открывается файл без flock

$handle fopen("/home/dmnorg/results.txt""r");
$contents fread($handlefilesize("/home/dmnorg/results.txt"));
fclose($handle);


??????????? Кто подскажет?

Оффлайн Alexey333

  • Фанат форума
  • Постоялец
  • ***
  • Сообщений: 107
  • +0/-0
  • 0
    • Просмотр профиля
Внесение изменений в текстовый файл
« Ответ #4 : 09 Декабря 2004, 08:16:58 »
У меня лично такой проблемы никогда не было, даже давно когда еще совсем не блокировал (был новичком). А когда начал блокировать, то тем более нет проблем.

Приведи весь скрипт. А то так не очень ясно из-за чего это. Может даже блокировка тут вообще ни при чем, а ошибка в самой программе (скорее всего из-за этого!).
И к тому же в первых 2 приведенных кодах я не вижу fclose. А fclose писать надо обязательно! Иначе такие проблемы могут случиться с большей вероятностью.

Оффлайн UltraMax

  • Завсегдатай
  • Пользователь
  • **
  • Сообщений: 98
  • +0/-0
  • 0
    • Просмотр профиля
    • http://www.dinamo-minsk.org
Внесение изменений в текстовый файл
« Ответ #5 : 09 Декабря 2004, 11:50:05 »
Вот коды/
Первый скрипт парсит POST данные из формы и добваляет их в текстовый файл

<?php
// variables
$first_place $_POST[\'first_place\'];
$second_place = $_POST[\'second_place\'];
$third_place = $_POST[\'third_place\'];
$real_name= $_POST[\'name\'];
$name= urlencode($_POST[\'name\']);
$email = $_POST[\'email\'];
$subject = "Голосование";
$rnd_val = rand (123456987, 987654321);
$string=$name."/".$email."/".$first_place."/".$second_place."/".$third_place."/".$rnd_val."/n\\n";
$message="<HTML><HEAD><meta http-equiv=\\"Content-Type\\" content=\\"text/html; charset=windows-1251\\"></HEAD><BODY><font face=Tahoma>Доброго времени суток, <B>$real_name</b>. Вы проголосовали за лучшего игрока сезона 2004 года.
<BR>Для того, чтобы активировать ваш голос, пожалуйста, перейдите по ссылке, указанной ниже.
<a href=http://xxx/vote/act.php?name=$name&email=$email&v1=$first_place&v2=$second_place&v3=$third_place&id=$rnd_val target=_blank>[url]http://xxx/vote/act.php?name=[/url]$name&email=$email&v1=$first_place&v2=$second_place&v3=$third_place&id=$rnd_val</a>
<BR>Всего наилучшего
<BR>UltraMax";
// To send HTML mail, you can set the Content-type header.
$headers  = "MIME-Version: 1.0\\r\\n";
$headers .= "Content-type: text/html; charset=Windows-1251\\r\\n";

// additional headers
$headers .= "From: Админ <mcsim@xxx.com>\\r\\n";

$handle = fopen("/home/dmnorg/results.txt", "r");
$contents = fread($handle, filesize("/home/dmnorg/results.txt"));
fclose($handle);

$pos = strpos(strtolower($contents), strtolower($email));
if ($pos === false) {
    $handle = fopen ("/home/dmnorg/results.txt", "a");
    if (flock($handle, LOCK_EX)) { // do an exclusive lock
    fwrite($handle, $string);
    flock($handle, LOCK_UN); // release the lock
    } else {
    echo "Couldn\'t lock the file !";
    }
    fclose($handle);
    mail($email, $subject, $message, $headers) || die ("<HTML><BODY><h2>Не удалось отправить письмо.  Попробуйте <a href=/vote/>вернуться</a> и попробовать еще раз</h2></BODY></HTML>");
    mail("mcsim@xxx.org", $subject, $message, $headers) || die ("<HTML><BODY><h2>Не удалось отправить письмо.  Попробуйте <a href=/vote/>вернуться</a> и попробовать еще раз</h2></BODY></HTML>");
    echo ("<HTML><HEAD><meta http-equiv=\\"Content-Type\\" content=\\"text/html; charset=windows-1251\\"></HEAD><BODY><h2><center>Спасибо!<P>На ваш e-mail <font color=blue>$email</font> выслано письмо с подтверждением голосования.</center></h2></BODY></HTML>");
    }
    else {
    echo "<HTML><HEAD><meta http-equiv=\\"Content-Type\\" content=\\"text/html; charset=windows-1251\\"></HEAD><BODY><h2><center>Данный адрес уже использовался для голосования!<P><A HREF=\\"javascript:history.go(-1)\\">Вернуться</A> и попробовать с другим адресом.</center></h2></BODY></HTML>";
}

?>


Второй скрипт изменяет строку в файле

<?php

$name 
$_GET[\'name\'];
$real_name= urldecode($_GET[\'name\']);
$email = $_GET[\'email\'];
$id = $_GET[\'id\'];
$v1 = $_GET[\'v1\'];
$v2 = $_GET[\'v2\'];
$v3 = $_GET[\'v3\'];

$str=$name."/".$email."/".$v1."/".$v2."/".$v3."/".$id."/n\\n";
$str_y=$name."/".$email."/".$v1."/".$v2."/".$v3."/".$id."/y\\n";

$handle = fopen("/home/dmnorg/results.txt", "r");
    if (flock($handle, LOCK_SH)) { // do an exclusive lock
    fwrite($handle, $contents_replaced);
    flock($handle, LOCK_UN); // release the lock
    }
    $contents = urldecode(fread($handle, filesize("/home/dmnorg/results.txt")));
fclose($handle);

//echo $str_y, $contents;
$posit = strpos(strtolower($contents), strtolower($str));
if ($posit === false) {
    echo "Внимание, ссылка активации неправильная. Вернитесь в вашу почту, и попытайтесь еще раз!";
    } else {
    $contents_replaced=substr_replace($contents, $str_y, $posit);
//    echo $contents_replaced;
    $handle = fopen ("/home/dmnorg/results.txt", "w");
    if (flock($handle, LOCK_EX)) { // do an exclusive lock
    fwrite($handle, $contents_replaced);
    flock($handle, LOCK_UN); // release the lock
    } else {
    echo "Couldn\'t lock the file !";
    }
    fclose($handle);
    echo ("<HTML><HEAD><meta http-equiv=\\"Content-Type\\" content=\\"text/html; charset=windows-1251\\"></HEAD><BODY><h2><center>Спасибо $real_name, ваш голос учтен!</center></h2></BODY></HTML>");
    }
?>


Понимаю что тут нет нормальной защиты, но на данный момент интересует почему строчки затираются...
Хотя вот сегодня утром пришел - все ок, с файлом работало нормально...
НЕ... в след. раз тока мускул.. тока мускул... Там такого быть не может :)

Оффлайн CGVictor

  • теперь местный
  • Глобальный модератор
  • Ветеран
  • *****
  • Сообщений: 2511
  • +0/-0
  • 2
    • Просмотр профиля
    • http://cg.net.ru
Внесение изменений в текстовый файл
« Ответ #6 : 09 Декабря 2004, 12:55:07 »
Про flock еще Spectator писал. Чем его способ не устраивает?
LJ: Backslashed life (rss)

Оффлайн UltraMax

  • Завсегдатай
  • Пользователь
  • **
  • Сообщений: 98
  • +0/-0
  • 0
    • Просмотр профиля
    • http://www.dinamo-minsk.org
Внесение изменений в текстовый файл
« Ответ #7 : 09 Декабря 2004, 13:06:44 »
CGVictor
ты имел ввиду вот это?
http://php.spb.ru/php/flock2.html
Давал бы сразу ссылку...
Заменил
$handle fopen ("/home/dmnorg/results.txt""w");
if (
flock($handleLOCK_EX)) { // do an exclusive lock

на
$handle fopen ("/home/dmnorg/results.txt""r+");
if (
flock($handleLOCK_EX)) { // do an exclusive lock
ftruncate($handle,0);  

сообщу будут ли затираться результаты
« Последнее редактирование: 09 Декабря 2004, 13:19:03 от UltraMax »

Оффлайн Djibo

  • Заглянувший
  • Новичок
  • *
  • Сообщений: 1
  • +0/-0
  • 0
    • Просмотр профиля
    • http://
Внесение изменений в текстовый файл
« Ответ #8 : 09 Декабря 2004, 14:12:47 »
нет, у спектатора через временный файл и ренейм.
http://spectator.ru/technology/php/flock_workaround

Оффлайн UltraMax

  • Завсегдатай
  • Пользователь
  • **
  • Сообщений: 98
  • +0/-0
  • 0
    • Просмотр профиля
    • http://www.dinamo-minsk.org
Внесение изменений в текстовый файл
« Ответ #9 : 09 Декабря 2004, 14:18:09 »
Да уже рассмотрел и этот вариант.
А кто скажет - что лучше
http://spectator.ru/technology/php/flock_workaround
или
http://php.spb.ru/php/flock2.html

Оффлайн Alexey333

  • Фанат форума
  • Постоялец
  • ***
  • Сообщений: 107
  • +0/-0
  • 0
    • Просмотр профиля
Внесение изменений в текстовый файл
« Ответ #10 : 09 Декабря 2004, 14:32:13 »
Ну и код у тебя запутанный. Уверен, что это чистая твоя ошибка, а не файлов. Ну сам подумай, если у других никогда такое не случается даже при большом количестве посетителей, а у тебя это случается постоянно. Проверь внимательно код и обязательно найдешь ошибку!
Я весь твой код проверять не стану, но вот некоторые ошибки бросаются в глаза:
$handle fopen("/home/dmnorg/results.txt""r"); 
    if (
flock($handleLOCK_SH)) { // do an exclusive lock 
    
fwrite($handle$contents_replaced); 
    
flock($handleLOCK_UN); // release the lock 
    



Открываешь файл на чтение "r", а сам пытаешься писать в него fwrite($handle, $contents_replaced); Это 100% ошибка, так как если хочешь писать, то надо использовать w или a.
К тому же не совсем понятно, что это за переменная $contents_replaced (до этого в скрипте она нигде не встречается).

В общем проверяй! ;)

Оффлайн UltraMax

  • Завсегдатай
  • Пользователь
  • **
  • Сообщений: 98
  • +0/-0
  • 0
    • Просмотр профиля
    • http://www.dinamo-minsk.org
Внесение изменений в текстовый файл
« Ответ #11 : 09 Декабря 2004, 17:42:58 »
Alexey333 да - это я лажанулся конкретно
Тут мне надо было прочитать файл, а я писать пытался. Я вообще отказываюсь понимать, с чего оно вообще работало дальше :)
Короче мне тут насоветовали после fwrite использовать fflush
Короче вот что у меня сейчас:
1. Чтение
$handle fopen("/home/dmnorg/results.txt""r");
    if (
flock($handleLOCK_SH)) { // do an exclusive lock
    
$handle fopen("/home/dmnorg/results.txt""r");
    
$contents urldecode(fread($handlefilesize("/home/dmnorg/results.txt")));
    
flock($handleLOCK_UN); // release the lock
    
}
fclose($handle);


2. Добавление
    $handle fopen ("/home/dmnorg/results.txt""a");
    if (
flock($handleLOCK_EX)) { // do an exclusive lock
    
fwrite($handle$string);
    
fflush($handle);
    
flock($handleLOCK_UN); // release the lock


3. Изменение
    $handle fopen ("/home/dmnorg/results.txt""r+");
    if (
flock($handleLOCK_EX)) { // do an exclusive lock
    
ftruncate($handle,0);
    
fwrite($handle$contents_replaced);
    
fflush($handle);
    
flock($handleLOCK_UN); // release the lock


Посмотрим что будет

PS - а что код запутанный.. да есть наверное
Но я по образованию бухгалтер, про правильность оформления кода мне никто не говорил. Есть ссыли - велком, почитаю :)
« Последнее редактирование: 09 Декабря 2004, 17:50:23 от UltraMax »

Оффлайн Alexey333

  • Фанат форума
  • Постоялец
  • ***
  • Сообщений: 107
  • +0/-0
  • 0
    • Просмотр профиля
Внесение изменений в текстовый файл
« Ответ #12 : 09 Декабря 2004, 18:57:46 »
Много возни из ничего. Советую больше внимания уделить написанию кода и его оформлению. А то выглядит так, что ты пытаешься свои ошибки свалить на файлы, будто это они во всем виноваты, а ты белый да пушистый.

Оффлайн UltraMax

  • Завсегдатай
  • Пользователь
  • **
  • Сообщений: 98
  • +0/-0
  • 0
    • Просмотр профиля
    • http://www.dinamo-minsk.org
Внесение изменений в текстовый файл
« Ответ #13 : 09 Декабря 2004, 19:05:14 »
Много шума?
Еслибы где-то здесь в, faq например, было описано КАК правильно лочить файлы, вопросов бы не возникло.
То что у меня что-то пропадало, это не из за того, что я ошибся, и  в файл открытый для чтения пытался что-то писать.
А в самом принципе работы fopen и flock
и эти принципы не понять из документации

Оффлайн Alexey333

  • Фанат форума
  • Постоялец
  • ***
  • Сообщений: 107
  • +0/-0
  • 0
    • Просмотр профиля
Внесение изменений в текстовый файл
« Ответ #14 : 09 Декабря 2004, 19:30:34 »
Ха, ни у кого (например, у меня) вообще никогда ничего не пропадает из-за одновременного доступа, а у тебя сразу пропадает. Если у меня что-то и пропадает, то я ищу ошибку в программе, нахожу ее, и все работает нормально. Никакая блокировка тут ни при чем. А у тебя больно высокое самомнение!
Я пишу так:
$fp=fopen ("users/sumdown.txt","a");
flock ($fp,2);
fputs ($fp,"#");
fputs ($fp,"0");
flock ($fp,3);
fclose ($fp);

и проблем нет. А у тебя вдруг куча ошибок вылазиет, и ты все сразу свалил на блокировку!

 

Sitemap 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28