PERL CGI程序

PERL CGI程序,perl,cgi,Perl,Cgi,我正在尝试一个基本的Perl/CGI脚本来跟踪访问网页的访问者。Perl代码如下所示: #!/usr/bin/perl #KEEPING COUNT OF VISITORS IN A FILE use CGI':standard'; print "content-type:text/html\n\n"; #opening file in read mode open (FILE,"<count.dat"); $cnt= <FILE>; close(FILE); $cnt=$cn

我正在尝试一个基本的Perl/CGI脚本来跟踪访问网页的访问者。Perl代码如下所示:

#!/usr/bin/perl
#KEEPING COUNT OF VISITORS IN A FILE
use CGI':standard';
print "content-type:text/html\n\n";
#opening file in read mode
open (FILE,"<count.dat");
$cnt= <FILE>;
close(FILE);
$cnt=$cnt+1;
#opening file to write
open(FILE,">count.dat");
print FILE $cnt;
close(FILE);
print "Visitor count: $cnt";
#/usr/bin/perl
#在档案中记录访客数量
使用CGI“:标准”;
打印“内容类型:text/html\n\n”;
#以读取模式打开文件
打开(文件“count.dat”);
打印文件$cnt;
关闭(文件);
打印“访客数量:$cnt”;

问题在于,每次刷新时,网页不会增加访问者的数量。计数保持初始值$cnt,即1。知道问题出在哪里吗?

您永远不会测试打开文件句柄的尝试是否有效。给定一个我有权读取和写入的文件,该文件只包含一个数字,没有其他内容,代码的行为符合预期。如果文件不存在,则计数将始终为
1
,如果它是只读的,则它将保持在文件开始的位置

更一般的建议:

  • 使用严格
    使用警告(并根据投诉纠正代码)
  • 根据使用三个参数调用
    open
  • 当你
    打开一个文件时,总是
    处理($!)中的错误
  • 不要用这样的文件来存储数据,你有潜在的竞争条件
  • 纠正

您永远不会测试打开文件句柄的尝试是否有效。给定一个我有权读取和写入的文件,该文件只包含一个数字,没有其他内容,代码的行为符合预期。如果文件不存在,则计数将始终为
1
,如果它是只读的,则它将保持在文件开始的位置

更一般的建议:

  • 使用严格
    使用警告(并根据投诉纠正代码)
  • 根据使用三个参数调用
    open
  • 当你
    打开一个文件时,总是
    处理($!)中的错误
  • 不要用这样的文件来存储数据,你有潜在的竞争条件
  • 纠正

    • 一些潜在原因:

      • “count.dat”未被
        打开
        读取。始终使用
        或die$进行测试至少检查文件是否打开

      • 代码没有被执行,而您认为是这样


        • 一些潜在原因:

          • “count.dat”未被
            打开
            读取。始终使用
            或die$进行测试至少检查文件是否打开

          • 代码没有被执行,而您认为是这样


          这里有一个替代解决方案,它只使用一个open()并在文件不存在时创建该文件。锁定消除了多个更新程序之间的潜在竞争条件

          #!/usr/bin/env perl
          use strict;
          use warnings;
          use Fcntl qw(:DEFAULT :flock);
          my $file = 'mycount';
          sysopen(my $fh, $file, O_RDWR|O_CREAT) or die "Can't open '$file' $!\n";
          flock($fh, LOCK_EX) or die "Can't lock $file: $!\n";
          my $cnt = <$fh>;
          $cnt=0 unless $cnt;
          $cnt++;
          seek $fh, 0, 0;
          print ${fh} $cnt;
          close $fh or die "Can't close $file: $\n";
          print "Visitor count: $cnt\n";
          
          #/usr/bin/env perl
          严格使用;
          使用警告;
          使用Fcntl qw(:默认值:flock);
          my$file='mycount';
          sysopen(我的$fh、$file、O|RDWR | O|u CREAT)或die“无法打开'$file'$!\n”;
          flock($fh,LOCK_EX)或die“无法锁定$file:$!\n”;
          我的$cnt=;
          $cnt=0,除非$cnt;
          $cnt++;
          寻求$fh,0,0;
          打印${fh}$cnt;
          关闭$fh或die“无法关闭$file:$\n”;
          打印“访客计数:$cnt\n”;
          
          这里有一个替代解决方案,它只使用一个open()并在文件不存在时创建该文件。锁定消除了多个更新程序之间的潜在竞争条件

          #!/usr/bin/env perl
          use strict;
          use warnings;
          use Fcntl qw(:DEFAULT :flock);
          my $file = 'mycount';
          sysopen(my $fh, $file, O_RDWR|O_CREAT) or die "Can't open '$file' $!\n";
          flock($fh, LOCK_EX) or die "Can't lock $file: $!\n";
          my $cnt = <$fh>;
          $cnt=0 unless $cnt;
          $cnt++;
          seek $fh, 0, 0;
          print ${fh} $cnt;
          close $fh or die "Can't close $file: $\n";
          print "Visitor count: $cnt\n";
          
          #/usr/bin/env perl
          严格使用;
          使用警告;
          使用Fcntl qw(:默认值:flock);
          my$file='mycount';
          sysopen(我的$fh、$file、O|RDWR | O|u CREAT)或die“无法打开'$file'$!\n”;
          flock($fh,LOCK_EX)或die“无法锁定$file:$!\n”;
          我的$cnt=;
          $cnt=0,除非$cnt;
          $cnt++;
          寻求$fh,0,0;
          打印${fh}$cnt;
          关闭$fh或die“无法关闭$file:$\n”;
          打印“访客计数:$cnt\n”;
          
          您需要关闭该网页,然后重新打开。仅仅刷新页面不会增加计数

          您需要关闭该网页,然后重新打开。仅仅刷新页面不会增加计数

          您可能忘记的最明显的事情是更改文件的权限
          count.dat
          这样做:

          sudo chmod 777 count.dat
          

          这应该可以做到

          最明显的一点是,您可能会忘记更改文件的权限
          count.dat
          这样做:

          sudo chmod 777 count.dat
          

          这应该能奏效

          谢谢你,伙计:)。我不是什么Perl程序员,这是我的第一个Perl CGI脚本:D.Btw,count.dat文件在哪里?我在cgi bin中找不到它。我使用UbuntuLinux。@amal antony-脚本希望它与脚本位于同一位置(尽管
          cgi-bin
          是保存此类数据的非常糟糕的位置),我已将其修复。文件权限有问题。再次感谢@Quentin脚本希望它位于当前工作目录中,该目录可能与脚本位于同一目录,也可能不是(!)。谢谢mate:)。我不是什么Perl程序员,这是我的第一个Perl CGI脚本:D.Btw,count.dat文件在哪里?我在cgi bin中找不到它。我使用UbuntuLinux。@amal antony-脚本希望它与脚本位于同一位置(尽管
          cgi-bin
          是保存此类数据的非常糟糕的位置),我已将其修复。文件权限有问题。再次感谢@Quentin脚本希望它位于当前工作目录中,该目录可能与脚本相同,也可能不相同(!)。如果您从未使用过它,为什么要包括
          CGI
          ?如果您从未使用过它,为什么要包括
          CGI
          ?这并不能解决问题或竞争条件。多个进程可以同时写入和读取。这并不能解决问题或争用条件。多个进程可以同时写入和读取。