【问题标题】:Why does directoryExists test true but cfdirectory fails?为什么 directoryExists 测试为 true 但 cfdirectory 失败?
【发布时间】:2014-05-27 14:54:19
【问题描述】:

我有一个访问内存文件的页面。我们有 10 - 20k 个文件存储在数百个目录中(最多 2000 个)。所有目录和文件都是以编程方式创建的。没有设置或更改权限。所有文件都使用默认的 CF 帐户,我们对此没有任何问题。

每隔一段时间,我们就会收到一个错误。我们测试目录的存在。如果它存在,我们获取目录的内容并对文件做一些事情。无论有没有内容,我们都能成功读取目录。

<cfscript>
    LOCAL.RamFileDir = "ram://CatSearchMenu/9160";
</cfscript>

<cfoutput>
<cfif directoryExists("#LOCAL.RamFileDir#") eq true>
    #LOCAL.RamFileDir# exists<br>
    <cfdirectory name="getRamFiles" directory="#LOCAL.RamFileDir#" action="list">
    <cfdump var="#getRamFiles#">
<cfelse>
    #LOCAL.RamFileDir# DOES NOT exist<br>
</cfif>     
</cfoutput>

这是我遇到的错误...

An error occurred when performing a file operation listFiles on file /CatSearchMenuSubCats/9160.

The cause of this exception was: org.apache.commons.vfs2.FileSystemException: Could not list the contents of folder "ram:///CatSearchMenuSubCats/9160"..

The error occurred in E:/INETPUB/WWWROOT/AVCATALOGS/...: line 92

 91 :                   <!--- GET THE FILES --->
 92 :                   <cfdirectory name="getRamFiles" 
 93 :                       directory="#LOCAL.RamFileDir#" 
 94 :                       action="list">

getFileInfo() 函数显示没有任何东西阻止我访问该目录。

下图显示的路径略有不同。为简洁起见,路径有所不同。

额外赏金信息 ~ 于 2014 年 6 月 9 日添加

这个特定目录通过了 directoryExists() 测试,但是当我们使用 cfdirectory 列出内容时,它会阻塞。怎么可能通过一次测试就失败了?

我们无法对此目录执行任何 cfdirectory 操作,创建、删除或列表操作都不起作用。但是,如果我们知道文件名,我们就可以访问目录中的文件。

当我们重新启动 ColdFusion 服务时,内存被清除了。自动地,文件由另一个进程根据需要创建。这些文件可以连续几天启动并运行并正常工作。然后,突然间,只有一个目录不可用。它永远不是同一个目录。几天后,ONE MORE 目录变得不可用。同样,每个其他目录(两千个)都可以完美运行。同样,任何目录中的所有文件都可以完全访问。一旦目录变得不可用,它就会一直保持这种状态,直到我们重新启动 ColdFusion 服务。

<cfscript>
// SET RAM FILE BASE
LOCAL.RamFileBase = "ram://includes";
</cfscript>

<!--- TEST THE BASE --->
<cfoutput>
<cfif directoryExists("#LOCAL.RamFileBase#") eq true>
<h1>#LOCAL.RamFileBase# BASE EXISTS</h1>

<!--- GET THE BASE --->
<cfdirectory name="getRamBase" directory="#LOCAL.RamFileBase#" action="list">

<!--- LOOP THROUGH THE BASE --->        
<cfloop query="getRamBase">

    <!--- TEST THE SUB DIRECTORY --->
    <cfif directoryExists("#LOCAL.RamFileBase#/#getRamBase.Name#") eq true>
        <h3>#LOCAL.RamFileBase#/#getRamBase.Name# SUB DIR EXISTS</h3>

        <!--- GET THE SUB DIRECTORY --->
        <cfdirectory name="getRamSubDir" directory="#LOCAL.RamFileBase#/#getRamBase.Name#" action="list">

        <!--- LOOP THROUGH THE SUB DIRECTORY --->
        <cfloop query="getRamSubDir">

            <!--- TEST THE SUB SUB DIRECTORY ~ WHERE THE FILES ARE --->
            <cfif directoryExists("#LOCAL.RamFileBase#/#getRamBase.Name#/#getRamSubDir.Name#") eq true>
                <b>#LOCAL.RamFileBase#/#getRamBase.Name#/#getRamSubDir.Name#</b> SUB SUB DIR EXISTS<br>

                <!--- GET THE FILES IN THE SUB SUB DIRECTORY --->
                                    <!--- THIS IS WHERE THE PROBLEM IS --->
                <cfdirectory name="getRamFiles" 
                        directory="#LOCAL.RamFileBase#/#getRamBase.Name#/#getRamSubDir.Name#" 
                        action="list" 
                        sort="DateLastModified ASC">

                    <!--- LOOP THROUGH THE FILES --->
                    <cfloop query="getRamFiles">

【问题讨论】:

  • 听起来您没有读取目录内容的权限?您可能想要使用 getFileInfo 元数据返回的canRead 属性,请参阅sagarganatra.com/2012/01/…
  • PS 你可以把&lt;cfif directoryExists("#LOCAL.RamFileDir#") eq true&gt;写成&lt;cfif directoryExists(LOCAL.RamFileDir)&gt;
  • 邓肯,是的,我可以去掉“eq true”以及英镑符号。你认为这是问题所在吗?
  • 你能分享更多的例外情况吗?
  • 等待...阅读异常。我错过了什么吗?它似乎指向不同的位置。 ram:///CatSearchMenuSubCats/9160ram:///includes/CatSearchMenuSubCats/9160 来自转储。只是有问题的不一致?

标签: coldfusion coldfusion-10


【解决方案1】:

一些观察和糟糕的 Adob​​e 文档:

使用LOCAL 范围可能没问题,但我不希望你这样做,因为代码不在函数内。

在浏览 Adob​​e 文档时,我注意到在引用内存文件时经常使用 3 个正斜杠。例如:ram:/// 不使用 3 可能是一个微妙的问题。

根据http://help.adobe.com/en_US/ColdFusion/10.0/Developing/WSe9cbe5cf462523a0-70e2363b121825b20e7-8000.html&lt;cfdirectory /&gt; 标签不会出现在“内存文件支持以下标签:”部分。这很麻烦,因为同一页面上该部分上方的示例使用&lt;cfdirectory /&gt;

最后,我不相信内存功能是为了处理存储在数百个目录中的 10-20k 文件。 :) 在 Web 根目录之外使用适当锁定的传统文件系统可能是更好的选择。

【讨论】:

  • 1) 是的,这里有更合适的范围。这个范围是它在函数中的保留。 2) 是的,Adbode 文档与其使用 2 或 3 个斜杠不一致。使用哪一个似乎没有任何区别。 3) CFDIRECTORY 标签工作得很好,不管文档说什么都支持。 4) 是什么让您认为该功能并不意味着支持我正在使用的文件和文件夹的数量?这只是猜测还是您有任何证据?
  • Adobe 文档指出“内存中”文件存储在 RAM 中。虽然文档没有在 RAM 中说“不要在数百个目录中存储 20k 文件”,但仍然出现了一个心理危险信号。如果您有足够的 RAM,您的 JVM 已正确调整,您的应用程序服务器不会遇到重大负载,并且您无需进行负载平衡,那么我想没有理由不继续您的实现。但是,您似乎遇到了细微的错误,因此提出了这个问题。祝你好运:)
  • 有足够的可用 RAM 并且 JVM 已正确调整。无论有 100 个或 100,000 个文件,都可能发生该错误。服务器可能会启动并运行数周而绝对没有问题,然后发生错误。似乎该文件夹已损坏,但该文件夹中的文件是完全可访问的。真是莫名其妙。
猜你喜欢
  • 1970-01-01
  • 2018-04-04
  • 2022-01-04
  • 2019-04-27
  • 2021-01-28
  • 2021-04-06
  • 1970-01-01
  • 2012-04-21
  • 1970-01-01
相关资源
最近更新 更多