php “glob” 和重复数据删除?

2022-08-30 22:28:37

我有一个php应用程序,它(每个请求)扫描某些文件的存在。(在网络共享上)

我正在使用这个,因为通常我只知道文件名的开头。glob

我注意到,这不会返回当前由任何客户端打开的文件,因此如果有人打开了它,我的应用程序认为不存在。globfile_xy

有没有办法让返回打开的(:=锁定?)文件也是如此?glob

奇怪的是,这一点没有提到。但是,我可以确认glob没有返回当前由客户端打开的文件...(一旦客户端关闭访问应用程序,将像往常一样返回文件)glob


ps.:只要文件打开,甚至不会返回文件。(网络共享允许最大并发用户数)glob("\\server\share\*")


    $dir = opendir ("\\server\share");
    while ($file = readdir($dir)){
      echo $file."<br />";
    }

显示有问题的文件完全正常,无论是否由另一个客户端打开。 - 所以我几乎可以排除任何访问限制/权限...


即使我现在不知道原因,我也弄清楚了原因:

当文件位于使用 Windows Server 2012 R2 内置重复数据删除功能的驱动器上时,将显示找不到打开的文件的问题。glob()

如果将文件移动到非重复数据删除共享,即使由多个客户端打开,也可以读取它。glob()


由于我有一个可行的替代方案,这个问题应该主要集中在为什么glob不起作用 - 或者让我们说在这里工作不同。在如何访问底层文件系统以确定内容方面必须存在差异。globreaddir


另一个证据

还有另一个证据,证明这与重复数据删除有关:我将该功能配置为“仅”删除超过3天的重复数据删除文件。

我设置了一个cronjob,“打开并清除”共享上的某个文件。一旦它大约3天(Windows决定何时进行重复数据删除),glob就无法列出该文件,而它是由另一个客户端打开的。

因此,glob 能够找到在前 3 天内复制到共享的打开文件 - 然后一旦重复数据删除,就会开始错过它。

观察

球形

glob失败,导致这篇文章:-)

scandir

使用上述函数显示完全相同的行为:scandir

  • 客户端打开的重复数据删除文件 - 结果数组中缺少
  • 客户端未打开的重复数据删除文件 - 结果数组的一部分。

打开目录 / 读取目录

我想再次强调,这两种情况下的工作都是如此。opendirreaddir

递归目录迭代器

这也在任何时候都产生了预期的结果。

文件属性

我注意到,重复数据删除的文件显示为“硬盘大小”为 0 字节,而尚未重复数据删除的文件(已成功找到)显示为它们在逻辑上占用的大小(基于文件系统群集大小):

但是,这并不能解释为什么客户端是否打开文件会有所不同。大小报告在任何时候都是相等的。

File Attributes of deduplicated and not deduplicated file


答案 1

我不确定这是否是您要查找的内容,但我使用scandir()列出目录中的所有文件,然后一旦知道名称,您就可以对它们执行任何命令。它也适用于打开的文件

PHP 扫描目录文档源


答案 2

如果重复数据删除的目的是不重复,那么文件被锁定并且php看不到它们,这是有一定道理的。唯一要做的就是看看这个限制是否也适用于scandir()和SPL目录/文件系统系列的迭代器。如果是这样,可能无法获得它们的列表。

唯一的另一个选择是使用exec()和Windows命令行类型的黑客,看看你是否可以获得文件列表,然后解析输出。这可能很有用

php exec: 不返回输出

祝你好运!


推荐