3

我在使用之前写了一些测试代码Proc::Daemon,我的测试代码是这样的:

#! /usr/bin/perl

use strict;
use warnings;
use Proc::Daemon;

Proc::Daemon::Init();
my $continue = 1;
$SIG{TERM} = sub { $continue = 0 ; }

while ( $continue ) {
    sleep(5) ;
    &greeting ;
}

sub greeting {
    open ( FH, ">>/home/daogu/foo" ) or die "can't open it" ;
    print FH "hello word\n" ;
    close FH ;
}

启动玩具守护进程后,我发现实际上没有任何内容写入“ foo”。谁能解释为什么会这样?谢谢。

4

2 回答 2

7

首先,您需要一个分号来终止第 9 行的赋值:

$SIG{TERM} = sub { $continue = 0 ; };

在我添加之前,您的程序甚至都不会运行,所以我猜您在脚本中有它并且在这里错过了它。

除此之外,我怀疑 Guss 是对的,而且您有权限问题。这是一种检查方法。打开一个单独的终端并运行top. 启动守护程序脚本,您将看到一个 Perl 进程出现。如果问题出在权限上,您很快就会看到 Perl 进程消失了。该脚本在子例程中终止,但您对有用错误消息的尝试永远不会出现,因为此时守护程序无法访问您的终端。

更改此测试的一种快速方法是在子程序中更改die为。warn如果您这样做,守护程序将永远继续运行(检查终端运行top以确认这一点)。但是,如果问题是权限,您仍然不会看到创建或写入文件。

编辑:是的,权限问题 + 无法访问 STDERR = 一个死的、静默的守护进程。试试这个版本,但请确保您可以写入您为 STDERR 切换的日志:

Proc::Daemon::Init();
my $continue = 1;
$SIG{TERM} = sub { $continue = 0 ; };

while ( $continue ) {
    sleep(5);
    greeting();
}

sub greeting {
    open STDERR, '>>', '/Users/telemachus/log'
        or die "Can't reopen STDERR to log: $!";
    open my $fh, '>>', '/usr/local/foo'
        or warn "Can't open /usr/local/foo for writing: $!";
    print $fh "hello word\n";
    close $fh;
}

您可能会在日志中看到很多这样的内容:

无法打开 foo 进行写入:在守护程序第 21 行拒绝权限。在守护程序第 22 行关闭文件句柄 $fh 上的 print()。

于 2009-08-16T16:26:03.803 回答
3

你的剧本对我来说很好。问题很可能只是文件权限 - 确保您对应该创建文件的目录具有写入权限,或者如果文件已经存在,则您对文件本身具有写入权限。

我在我的机器上运行你的脚本,它工作正常。

于 2009-08-16T15:55:47.070 回答