2011-03-27 59 views
5

我有一个新人(隔壁的少年)写一些php代码来跟踪我的网站上的一些用法。我对PHP不熟悉,所以我想问一下关于并发文件访问的问题。文件锁定在PHP

我的本地应用程序(在Windows上)偶尔会通过点击包含我的php脚本的URL将一些数据记录到我的网站。本机应用程序不检查返回的数据。

 $fh = fopen($updateFile, 'a') or die("can't open file"); 
     fwrite($fh, $ip); 
     fwrite($fh, ', '); 
     fwrite($fh, $date); 
     fwrite($fh, ', '); 
     fwrite($fh, implode(', ', $_GET)); 
     fwrite($fh, "\r\n"); 
     fclose($fh); 

这是一个低流量的网站,数据并不重要。但是如果两个用户发生冲突并且脚本的两个实例都尝试向该文件添加一行,会发生什么情况?有没有在PHP中隐式文件锁定?

上面的代码是否至少安全无法锁定并永远不会将控制权返回给我的用户?该文件可能被破坏?如果我有上面的脚本每个月删除文件,如果脚本的另一个实例正在写入文件中,会发生什么情况?

回答

9

你应该把该文件锁:

<?php 
$fp = fopen($updateFile, 'w+'); 
if(flock($fp, LOCK_EX)) { 
fwrite($fp, 'a'); 
flock($fp, LOCK_UN); 
} else { 
echo 'can\'t lock'; 
} 

fclose($fp); 
+0

正是我在找的,雷蒙德。谢谢。从我刚刚完成的其他阅读(http://www.tuxradar.com/practicalphp/8/11/0),看起来可能永远不会达到echo-statement。在第一个进程解锁文件之前,第二个进程是否会阻止群集调用?羊群不需要OR LOCK_NB以便能够达到回声声明吗? – RobertFrank 2011-03-27 14:36:45

+0

我本来希望得到何先生或其他人的回应,我的观察是否会达到上述回声。 – RobertFrank 2011-03-30 12:00:05

+4

是的,你需要在代码中使用'| LOCK_NB',否则如果锁已经被锁定,锁就会被锁住:) – cweiske 2011-05-07 10:37:12

3

因为这是一个附加到文件,最好的办法是汇总数据,并在一个FWRITE写入文件()提供要写入的数据并不比文件缓冲区大。当然,你并不总是知道缓冲区的大小,所以flock();总是一个不错的选择。

+0

我会做两个:保持写入一个'fwrite()'*和*锁定文件。在一些Linux平台和一些较旧的文件系统上,'flock()'可能实际上不锁定文件。 – Jason 2015-10-27 12:34:18