您的位置:首页 > 编程语言 > PHP开发

请写一段 PHP 代码 ,确保多个进程同时写入同一个文件成功

2017-09-27 15:52 639 查看
方案一:

function writeData($filepath, $data)
{
$fp = fopen($filepath,'a');
do{
usleep(100);
}while (!flock($fp, LOCK_EX));

$res = fwrite($fp, $data."\n");
flock($fp, LOCK_UN);
fclose($fp);
return $res;
}


本文出自 “我知” 博客,请务必保留此出处http://iknow.blog.51cto.com/6209466/1058876

方案二:

function writeData($path, $mode,$data,$max_retries = 10)
{
$fp = fopen($path, $mode);
$retries = 0;
do{
if ($retries > 0)
{
usleep(rand(1, 10000));
}
$retries += 1;
}while (!flock($fp, LOCK_EX) and $retries<= $max_retries);
//判断是否等于最大重试次数,是则返回false
if ($retries == $max_retries)
{
return false;
}
fwrite($fp, "$data
");
flock($fp, LOCK_UN);
fclose($fp);
return true;
}


来自http://www.xuejiehome.com/blread-1670.html

方案三:

function write_file($filename, $content)
{
$lock = $filename . '.lck';
$write_length = 0;
while(true) {
if( file_exists($lock) ) {
usleep(100);
} else {
touch($lock);
$write_length = file_put_contents($filename, $content, FILE_APPEND);
break;
}
}
if( file_exists($lock) ) {
unlink($lock);
}
return $write_length;
}



flock

(PHP 4, PHP 5, PHP 7)

flock — 轻便的咨询文件锁定

bool flock ( resource $handle , int $operation [, int &$wouldblock ] )


flock() 允许执行一个简单的可以在任何平台中使用的读取/写入模型(包括大部分的 Unix 派生版和甚至是 Windows)。

在 PHP 5.3.2版本之前,锁也会被 fclose() 释放(在脚本结束后会自动调用)。

PHP 支持以咨询方式(也就是说所有访问程序必须使用同一方式锁定, 否则它不会工作)锁定全部文件的一种轻便方法。 默认情况下,这个函数会阻塞到获取锁;这可以通过下面文档中
LOCK_NB
选项来控制(在非 Windows 平台上)。


参数

handle

文件系统指针,是典型地由 fopen() 创建的 resource(资源)。
operation

operation
可以是以下值之一:

LOCK_SH
取得共享锁定(读取的程序)。
LOCK_EX
取得独占锁定(写入的程序。
LOCK_UN
释放锁定(无论共享或独占)。

如果不希望 flock() 在锁定时堵塞,则是
LOCK_NB
(Windows 上还不支持)。
wouldblock

如果锁定会堵塞的话(EWOULDBLOCK 错误码情况下),可选的第三个参数会被设置为
TRUE
。(Windows 上不支持)


返回值

成功时返回
TRUE
, 或者在失败时返回
FALSE


Example #1 flock() 例子

<?php

$fp = fopen("/tmp/lock.txt", "r+");

if (flock($fp, LOCK_EX)) {  // 进行排它型锁定
ftruncate($fp, 0);      // truncate file
fwrite($fp, "Write something here\n");
fflush($fp);            // flush output before releasing the lock
flock($fp, LOCK_UN);    // 释放锁定
} else {
echo "Couldn't get the lock!";
}

fclose($fp);

?>


Example #2 flock() 使用
LOCK_NB
选项

<?php
$fp = fopen('/tmp/lock.txt', 'r+');

/* Activate the LOCK_NB option on an LOCK_EX operation */
if(!flock($fp, LOCK_EX | LOCK_NB)) {
echo 'Unable to obtain lock';
exit(-1);
}

/* ... */

fclose($fp);
?>


Note:

由于 flock() 需要一个文件指针, 因此可能不得不用一个特殊的锁定文件来保护打算通过写模式打开的文件的访问(在 fopen() 函数中加入
"w" 或 "w+")。

Warning:

在部分操作系统中 flock() 以进程级实现。当用一个多线程服务器 API(比如 ISAPI)时,可能不可以依靠 flock() 来保护文件,因为运行于同一服务器实例中其它并行线程的 PHP 脚本可以对该文件进行处理。

flock() 不支持旧的文件系统,如 FAT 以及它的派生系统。因此,此环境下总是返回
FALSE
(尤其是对 Windows 98 用户来说)。

http://php.net/manual/zh/function.flock.php

来源:http://www.cnblogs.com/gengyi/p/6399206.html
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: