我正在开发一个与名为Dazzle的USPS运送包裹对接的系统。该系统的一部分包括一个监视守护程序,该守护程序的目的是获取用制表符分隔的值文件,将它们转换为Dazzle可以识别的XML,然后将它们传递给Dazzle以生成标签。这部分工作正常。但是,我还想做的是解析Dazzle生成的输出文件并将其导入数据库。
请注意,Dazzle在Windows上运行。我的监视守护程序是用Perl编写的,并且可以在Linux上运行。我的Linux系统具有通过Samba挂载的Dazzle的输入和输出目录。
在Dazzle开始写入输出文件与完成输出文件之间,存在可测量的延迟。我想知道的是如何等待Dazzle完成写入输出文件?我尝试打开文件并对其进行flock($fh, LOCK_SH)
,但这似乎没有任何效果。
编辑:我有一个基于以下“mobrule”评论的想法。 Dazzle用XML编写输出文件。装运中的每个包裹都包含在标签中,整个文档都包含在标签中。因此,如果我在文件完成之前开始读取文件,则可以在执行操作之前简单地等待适当的结束标记。
另外,我应该提到我目前在做什么。当我检测到已创建输出XML文件时,我尝试对其进行解析。如果解析失败,我会 sleep ,然后重试。如果失败,我睡两次,然后再试一次,依此类推。在具有64秒超时的测试中,此方法效果很好。
最佳答案
没有通用且可移植的方法来判断某个进程是否对某个任意文件具有打开的文件句柄。您必须根据本地的情况做出判断。
在这种情况下,可以在Windows计算机上查询进程表,以查看“Dazzle”程序是否仍在运行。或者,也许您的经验为您提供了其他指导,例如“在合理的输入下,Dazzle的运行时间不会超过20秒”或“在Dazzle的运行时,它每隔几秒钟更新一次文件。如果尚未更新文件,在10秒内,那么Dazzle很有可能会完成。”
但是您不必等到Dazzle完成。完全可以在Dazzle写入文件的同时读取文件-参见the perldoc for the seek
function,注意有关“如何模拟tail -f
”的部分。然后,您可以在Dazzle运行时更新数据库。
这样,如果您对Dazzle完成时间的猜测过于保守,则数据库仍将及时更新,唯一的代价就是在EOF上对文件句柄的无用查找和读取调用。