1

我正在使用 Delphi 和ReadDirectoryChangesW(in a TThread) 来检测特定文件夹何时发生更改。这工作得很好。我需要知道更改何时完成,以便我可以安全地对文件执行某些操作。

这是场景:我已将打印机映射到特定的文件名和文件夹(文件:本地端口c:\MonitorMe\prinfil.dat)。该文件夹中的唯一文件将是该打印机文件。打印作业可以是单页,也可以是数百页——我必须等到“打印到文件”完成后才能触发进一步的操作。我正在监视FILE_NOTIFY_CHANGE_SIZE并且FILE_NOTIFY_CHANGE_LAST_WRITE- 所以我会定期收到文件仍在“正在打印到”的通知。

我正在寻找一种安全的方法来实际检测“打印”何时完成。我想我可以在表单中设置一个计时器,然后Synchronize(StillPrinting)在线程中调用。StillPrinting将停止并重新启动计时器,以便只有在大约 300 毫秒的 NO 文件夹更改之后,计时器才会执行 - 触发OnAfterPrintComplete事件。这似乎很危险。

我可以寻找什么来确定文件保存是否已完成?

4

1 回答 1

4

“文件已完成”是主观的 - 只需考虑 5 分钟,您就会得出结论,您要求的东西很少有意义:

  • 写入速度可能会有所不同:您可能希望在一个系统上 2 秒内写入文件,而在另一个系统上则需要 5 分钟。
  • 划定界限:您认为在什么时候完成“写入”以及在什么时候附加到现有文件的其他写入?关于可能需要 2 年才能再次写入该文件的日志。同样,无论出于何种原因,您的打印机作业/程序可能会空闲 10 分钟,但仍可以访问该文件。
  • 修改:一个从字节 1 写入到 52000 但之后字节 10 到 19 被覆盖的文件怎么办?什么时候被认为是“完成”?
  • 即使SetEndOfFile()仅在给定点“剪切”(或扩展)文件,但没有人知道是否会在任何位置发生额外的写入。

不,但是有多种方法可以实现相同的目标:

  • 设置文件属性,即R可以发出不再发生写入的信号。因为您作为消费者无论如何都只想要读取权限。当然,“打印机”必须设置它。
  • 检查文件内容是否有有效的页脚,或者其任何格式似乎不完整。这都需要您知道打印文件格式和打印文件完全有格式(而不仅仅是二进制流)。
  • 尝试在没有任何共享权限的情况下打开文件(甚至没有FILE_SHARE_READ) - 只要另一个进程访问该文件,这就会失败。您可以预期打印机作业不会多次打开/关闭文件(尽管这也是可能的)。
  • 滥用文件作为“写入完成”标记:如果文件已被写入,则创建另一个(空)文件,其存在本身就表明另一个文件已完成。根据您的打印作业/程序,您可以添加另一个简短/简单的打印任务,并判断只要存在 2 个文件,就必须完成一个感兴趣的文件(而另一个与您无关)。
于 2020-10-14T08:44:41.887 回答