интерфейс командной строки — использование блокировки файлов для обеспечения того, чтобы скрипт PHP Daemon запускался только один раз

Я написал простую функцию, используемую для определения того, запущен ли уже скрипт, и предотвращения дублирования процессов:

class SomeClass{
public static function processLock($name)
{
$lockFile = "/tmp/" . $name;
$fp       = fopen($lockFile, "w+");

if ($fp === false)
{
echo "Already running.\n";
exit;
}
else
{
if ( ! flock($fp, LOCK_EX | LOCK_NB))
{
echo "Already running.\n";
exit;
}
}

return $fp;
}
}

Затем я могу вызвать такую ​​функцию вверху скрипта php:

Script_A:

<?

include_once "/SomeClass.php";

$lock = SomeClass::processLock("script_A_lock");

и это прекрасно работает ….. 99% времени. Однако иногда я обнаруживаю, что «script_A» не работает (он должен всегда работать).

Тогда я бегу lsof /tmp/script_A_lock чтобы понять, почему «script_A» не запускается.

Результаты не имеют смысла! Я получаю что-то вроде этого:

COMMAND    PID     .........     NAME
Script_B   234     .........     script_A_lock

Несвязанный скрипт «script_B» как-то украл блокировку файла!

Так:

  1. Как это происходит? Слово «script_A_lock» ТОЛЬКО появляется в Script_A (я искал весь проект), а Script_A НИКОГДА не включен.
  2. Как я могу предотвратить это? Очевидно, что только скрипт A должен содержать «script_A_lock».

0

Решение

Этот подход я обычно использую для файла блокировки. Если файл не существует, создайте его, что означает, что процесс выполняется. Обязательно отсоедините его в конце.

#!/usr/bin/php
<?php
define('LOCK_FILE',__FILE__.'lock');
if (!is_file(LOCK_FILE)) {
touch(LOCK_FILE);
echo 'Do stuff'.PHP_EOL;
unlink(LOCK_FILE);
} else {
echo 'Lock file found'.PHP_EOL;
}

Функция flock предназначена для поддержки нескольких скриптов, обращающихся к одному файлу, она не предназначена для использования в качестве файла блокировки. http://php.net/manual/en/function.flock.php

0

Другие решения

Других решений пока нет …

По вопросам рекламы ammmcru@yandex.ru
Adblock
detector