【问题标题】:file_exists doesn't seem to work correctlyfile_exists 似乎无法正常工作
【发布时间】:2013-02-17 19:17:30
【问题描述】:

我有一个我想要执行的 php 脚本,但前提是该脚本的其他实例尚未运行。我有这个代码:

$lockfile = __DIR__.'/lock.file';

if(file_exists($lockfile) == false)
{
    echo 'no lockfile. Job will execute.';
    $handle = fopen($lockfile, 'x') or die('Cannot open file:  '.$lockfile);
    $data = 'This is the lockfile';
    fwrite($handle, $data);
    fclose($lockfile);

    createLinks();

    unlink($lockfile);
}
else
{
    echo 'Lockfile present, job will not execute. Please try again later';
}

但它不能正确检查文件是否存在。如果我用浏览器调用脚本,lock.file 会正确创建(我可以用 ftp 看到它),然后删除。但是,我仍然可以同时多次运行该脚本。如果我自己用 ftp 创建一个 lock.file,它不会执行脚本。我已经搜索了几个小时了,会是什么?也许我很愚蠢,但我认为这应该可行,对吧?

编辑: 杰普,羊群做到了。非常感谢!最终代码:

$lockfile = __DIR__.'/lock.file';
$handle = fopen($lockfile, "x");

if(flock($handle, LOCK_EX))
{
    echo 'no lockfile. Job will execute.';

    $data = 'This is the lockfile';
    fwrite($handle, $data);

    createLinks();

    fclose($lockfile);  
    unlink($lockfile);
}
else
{
    echo 'Lockfile present, job will not execute. Please try again later';
}

【问题讨论】:

标签: php file-permissions file-exists


【解决方案1】:

来自file_exists的文档:

注意:这个函数的结果是缓存的。有关详细信息,请参阅 clearstatcache()。`

和:

您还应该注意,PHP 不会缓存有关不存在文件的信息。因此,如果您对一个不存在的文件调用 file_exists(),它将返回 FALSE,直到您创建该文件。如果您创建该文件,即使您随后删除该文件,它也会返回 TRUE。但是 unlink() 会自动清除缓存

尝试将您的功能更改为:

if(file_exists($lockfile) == false)
{
    clearstatcache();
    ...

看看clearstatcache()

【讨论】:

  • 请停止对不是code的东西使用代码块。
  • 哦,对不起,我现在才从您的编辑中意识到什么是正确的书写方式,谢谢!
  • 我设法通过谷歌找到了它(这里没有使用常见问题解答链接),所以现在我知道它是如何工作的了,谢谢!
【解决方案2】:

我今天花了半天时间来处理和你几乎一样的问题。我的 PHP 代码也使用了文件锁,并在其中调用了 file_exists()。我在“奇怪的” file_exists() 结果中遇到了同样的问题。当我将文件的使用(以获得锁)更改为数据库的使用时,我完全感到困惑——锁对应于表中的一行。结果完全一样 - 我尝试在浏览器的不同选项卡中同时启动代码,但我仍然未能获得锁定。

然后我意识到这种奇怪行为的真正原因是什么。在我的情况下(看起来你的情况是一样的),主要问题是脚本是在一个浏览器中“同时多次”启动的。但是请求不是同时处理的,而是顺序处理的。这里给出了对这种效果的一个很好的解释: https://stackoverflow.com/a/3623584/1758680

因此,所有请求都按顺序排列 - 每个请求都在等待前一个请求结束。每个锁都在下一个脚本开始并尝试获取锁之前被释放。

【讨论】:

  • 感谢您的评论。但是,这不是我的问题,也不是解决方案。如您所见,我的脚本没有连续运行,它们只会忽略锁定文件的存在并开始运行。这与进程运行的顺序没有任何关系,它与 fopen 不是创建和搜索锁定文件的正确方法有关。就像我上面解释的那样,flock 成功了。
【解决方案3】:

试试

$lockfile = 'lock.file';

或其他..

【讨论】:

    猜你喜欢
    • 2017-09-04
    • 2012-05-06
    • 2017-10-09
    • 2017-08-03
    • 2014-05-02
    • 2011-09-11
    • 2016-02-11
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多