(PHP 4, PHP 5, PHP 7, PHP 8)
flock — Блокирует файл методом переносимой рекомендательной блокировки
Функция flock() разрешает выполнять простую модель чтения-записи, которая будет работать на большей части Unix-платформ и даже на платформах семейства Windows.
Блокировку также снимает функция fclose()
или сборщик мусора, когда уничтожает поток stream
.
PHP поддерживает способ полной переносимой рекомендательной блокировки
файлов. То есть каждая программа, которая получает доступ к файлу,
должна использовать один и тот же способ блокировки, иначе блокировка не будет
работать. По умолчанию функция будет блокироваться до тех пор,
пока запрошенная блокировка не будет получена; это поведение изменяют
через описанный ниже флаг LOCK_NB
.
stream
Ресурс (resource) указателя файловой системы, который обычно создают функцией fopen().
operation
operation
принимает следующие значения:
LOCK_SH
для получения разделяемой блокировки (чтение).
LOCK_EX
для получения эксклюзивной блокировки (запись).
LOCK_UN
для снятия блокировки (разделяемой или эксклюзивной).
Флаг LOCK_NB
добавляют
как битовую маску к одной операции из списка выше,
если функция flock() не должна
блокироваться во время попытки блокировки файла.
would_block
Необязательный третий параметр получает значение 1, если блокировка будет блокирующей (в переменную errno будет записан код ошибки EWOULDBLOCK).
Функция возвращает true
, если выполнилась успешно, или false
, если возникла ошибка.
Пример #1 Пример использования функции flock()
<?php
$fp = fopen("/tmp/lock.txt", "r+");
if (flock($fp, LOCK_EX)) { // Выполняем эксклюзивную блокировку
ftruncate($fp, 0); // Очищаем файл
fwrite($fp, "Пишем что-нибудь сюда\n");
fflush($fp); // Очищаем вывод перед отменой блокировки
flock($fp, LOCK_UN); // Снимаем блокировку
} else {
echo "Не удалось получить блокировку!";
}
fclose($fp);
?>
Пример #2 Использование функции flock() с параметром LOCK_NB
<?php
$fp = fopen('/tmp/lock.txt', 'r+');
/* Включаем опцию LOCK_NB в операцию LOCK_EX */
if (!flock($fp, LOCK_EX | LOCK_NB)) {
echo 'Не удалось получить блокировку';
exit(-1);
}
/* ... */
fclose($fp);
?>
Замечание:
В системах Windows функция flock() включает обязательную блокировку вместо рекомендательной. Обязательная блокировка также поддерживается в операционных системах на базе Linux и System V через стандартный механизм, который поддерживает системный вызов fcntl(): то есть, если для файла установлен бит разрешения setgid и сброшен бит группового выполнения. Чтобы схема работала корректно в Linux, файловую систему также нужно смонтировать с опцией mand.
Замечание:
Поскольку функция flock() требует указатель на файл, возможно, придётся использовать специальный файл блокировки, чтобы защитить доступ к файлу, который вы собираетесь обрезать, открыв в режиме записи (в режимах «w» или «w+» в качестве аргумента функции fopen()).
Замечание:
Функцию разрешено вызывать только на дескрипторах локальных файлов, которые возвращает функция fopen(), или файловых дескрипторах пользовательских потоков, которые реализуют метод streamWrapper::stream_lock().
Присвоение другого значения параметру stream
в следующем дальше коде снимет текущую блокировку.
В ряде операционных систем функция flock() работает на уровне процессов. При работе с многопоточными серверными API, например, ISAPI, нельзя полагаться на функцию flock(), чтобы защитить файлы от других PHP-скриптов, которые работают в параллельном потоке на том же сервере!
Функцию flock() не поддерживают старые файловые системы
наподобие FAT
и её производные, поэтому функцию будет
возвращать false
в этих окружениях.
Замечание:
Если в Windows процесс блокировки открывает файл во второй раз, он не может получить доступ к файлу через второй дескриптор, пока не разблокирует файл.