如何在 perl 中不锁定日志文件

发布于 2024-10-30 22:18:23 字数 349 浏览 1 评论 0原文

这就是我现在正在做的事情,但它锁定了文件。

#!/usr/bin/perl
use Env qw( $USERNAME );
use File::Tail;
use strict;
use warnings;

my $file = $ARGV[0];

print "$file\n";

my $fileTail = File::Tail->new( name=>$file, maxinterval=>5, tail=>-1);
my $line;

while ( defined( $line = $fileTail->read ) )
{
    print $line;
}

exit;

This is how I am doing it right now but it locks the file.

#!/usr/bin/perl
use Env qw( $USERNAME );
use File::Tail;
use strict;
use warnings;

my $file = $ARGV[0];

print "$file\n";

my $fileTail = File::Tail->new( name=>$file, maxinterval=>5, tail=>-1);
my $line;

while ( defined( $line = $fileTail->read ) )
{
    print $line;
}

exit;

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

北城半夏 2024-11-06 22:18:23

根据文档,它不应该被锁定。你的操作系统是什么?我想知道您是否使用 Windows,尽管 shebang 行表明不是。因此,有关您的环境的更多详细信息将会有所帮助。

According to the documentation, it shouldn't be locking. What is your operating system though? I wonder if you are using Windows, although the shebang line suggests not. Some more details on your environment would therefore be helpful.

天涯沦落人 2024-11-06 22:18:23

Windows(或 NTFS...或者 Perl 如何在 Windows 上实现 open...不太确定)在 open() 中引入了强制锁定。如果您打开文件进行读取,其他人将无法打开它进行写入。如果您打开文件进行写入,其他人将无法打开它进行读取或写入。

您将文件保持打开状态以供读取,因此没有人可以写入日志。我认为这就是正在发生的事情。 File::Tail 可能没有解释这一点。它之所以有效,是因为 File::Tail 似乎会不时关闭并重新打开文件句柄,如果它没有看到任何活动,它会假设它已被截断或重新创建。这会释放您的锁定并让其他文件溜进去写入。

您可以通过使用一个 Perl 进程打开一个文件进行读取来测试这一点,然后尝试打开它以供另一个进程附加。

我相信解决这个问题的一种方法是使用 Windows 特定功能打开日志文件,这些功能允许您控制锁定行为。 Win32::SharedFileOpen 似乎就是这样。

fsopen(my $fh, $file, 'r', SH_DENYNO) or
    die "Can't read '$file' with no locks: $!\n";

这将打开一个文件以进行无锁读取。不幸的是,您负责完成其余的工作。 perlfaq 可能会有所帮助。

Windows (or NTFS... or how Perl implements open on Windows... not exactly sure) has mandatory locking rolled into open(). If you open a file for reading, others will not be able to open it for writing. If you open a file for writing, others will not be able to open it for reading or writing.

You're holding the file open for reading, so nobody can write to the log. I think that's what's happening. File::Tail probably doesn't account for this. It's working at all because File::Tail seems to close and reopen the filehandle from time to time if it doesn't see any activity, it assumes it's been truncated or recreated. This releases your lock and lets other files slip in to write.

You can test this by opening a file for reading with one Perl process, and then try to open it for appending by another.

I believe one way to deal with this is to open the log file using Windows specific functions that allow you to control the locking behavior. Win32::SharedFileOpen seems to be the thing.

fsopen(my $fh, $file, 'r', SH_DENYNO) or
    die "Can't read '$file' with no locks: $!\n";

That will open a file for reading with no locks. Unfortunately, you're responsible for doing the rest of the work. The perlfaq might help.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文