使用 Perl CGI 脚本上传文件不起作用
File upload using a Perl CGI script not working
以下代码没有任何语法错误,但仍然没有 working.Can 我为 $Domain 使用服务器 ip(如 100.100.100.100),并且应该为 $directory(i是指添加服务器IP还是域名?请帮忙
#!/usr/bin/perl
use CGI;
$CGI::POST_MAX= 100 * 1024;
$CGI::DISABLE_UPLOADS=0;
$Referer = $ENV{HTTP_REFERER};
$Domain = "xxx.com";
$cgi = new CGI;
$file=$cgi->upload('text');
print $cgi->header,
$cgi->start_html
(
-title=>'CGI.pm File Upload'
);
print <<EOF;
<form action="" method="post" enctype="multipart/form-data">
<input type="file" name="text" size=60><br>
<input type="submit" value="Upload">
</form>
EOF
if($file)
{
if($Referer =~ "$Domain")
{
$directory="var/www/cgi-bin/uploads";
open UPLOAD, ">$directory$file";
binmode UPLOAD;
while(<$file>) {print UPLOAD;}
close UPLOAD;
}
}
$cgi->end_html;
exit;
看来您需要再读一遍 the documentation on file upload basics。他们的示例代码是:
use autodie;
# undef may be returned if it's not a valid file handle
if ( my $io_handle = $q->upload('field_name') ) {
open ( my $out_file,'>>','/usr/local/web/users/feedback' );
while ( my $bytesread = $io_handle->read($buffer,1024) ) {
print $out_file $buffer;
}
}
您的代码在风格上存在一些差异,但需要注意的重要一点是,当您的代码运行此行时:
$file=$cgi->upload('text');
然后 $file
包含一个打开的文件句柄。它不包含文件名。这意味着您的代码的这些行中至少存在三个错误:
$directory="var/www/cgi-bin/uploads";
open UPLOAD, ">$directory$file";
- 您存储在
$directory
中的值几乎肯定会以 /
开头(所以它是 /var/www/cgi-bin/uploads
)。
- 您还需要在
$directory
和 $file
之间添加另一个 /
(否则,它将包含类似 /var/www/cgi-bin/uploadsmyfile.dat
的内容)。
- 您需要调用
$cgi->param('text')
来获取正在上传的文件的名称。
这就是阻止您的程序运行的原因。您的代码的上传部分应如下所示:
my $filename = $cgi->param('text');
my $fh = $cgi->upload('text');
my $directory = '/var/www/cgi-bin/uploads';
open my $upload_fh, '>', "$directory/$filename"
or die "Can't open '$directory/$filename': $!";
print $upload_fh $_ while <$fh>;
请注意,我在此处进行了一些风格上的改进:
- 使用了
open()
的 3 参数版本
- 使用词法文件句柄
- 检查
open()
调用是否成功,如果失败则终止程序并显示一条有用的错误消息
总而言之,您似乎是从已经过时大约二十年的资源中学习 CGI 编程的。您的代码看起来像是来自 1990 年代。
其他一些提示:
- 总是
use strict
和 use warnings
。
- 间接对象表示法 (
new CGI
) 可能非常混乱。请改用 CGI->new
。
- 我们知道 CGI.pm 中的 HTML 生成函数自上个千年末以来就是一个糟糕的想法。请不要使用它们。 Perl 有许多优秀的模板解决方案。
- 在 2017 年编写 CGI 程序是一个糟糕的想法。查看 CGI::Alternatives 了解现代 Perl Web 开发工具的介绍。
以下代码没有任何语法错误,但仍然没有 working.Can 我为 $Domain 使用服务器 ip(如 100.100.100.100),并且应该为 $directory(i是指添加服务器IP还是域名?请帮忙
#!/usr/bin/perl
use CGI;
$CGI::POST_MAX= 100 * 1024;
$CGI::DISABLE_UPLOADS=0;
$Referer = $ENV{HTTP_REFERER};
$Domain = "xxx.com";
$cgi = new CGI;
$file=$cgi->upload('text');
print $cgi->header,
$cgi->start_html
(
-title=>'CGI.pm File Upload'
);
print <<EOF;
<form action="" method="post" enctype="multipart/form-data">
<input type="file" name="text" size=60><br>
<input type="submit" value="Upload">
</form>
EOF
if($file)
{
if($Referer =~ "$Domain")
{
$directory="var/www/cgi-bin/uploads";
open UPLOAD, ">$directory$file";
binmode UPLOAD;
while(<$file>) {print UPLOAD;}
close UPLOAD;
}
}
$cgi->end_html;
exit;
看来您需要再读一遍 the documentation on file upload basics。他们的示例代码是:
use autodie;
# undef may be returned if it's not a valid file handle
if ( my $io_handle = $q->upload('field_name') ) {
open ( my $out_file,'>>','/usr/local/web/users/feedback' );
while ( my $bytesread = $io_handle->read($buffer,1024) ) {
print $out_file $buffer;
}
}
您的代码在风格上存在一些差异,但需要注意的重要一点是,当您的代码运行此行时:
$file=$cgi->upload('text');
然后 $file
包含一个打开的文件句柄。它不包含文件名。这意味着您的代码的这些行中至少存在三个错误:
$directory="var/www/cgi-bin/uploads";
open UPLOAD, ">$directory$file";
- 您存储在
$directory
中的值几乎肯定会以/
开头(所以它是/var/www/cgi-bin/uploads
)。 - 您还需要在
$directory
和$file
之间添加另一个/
(否则,它将包含类似/var/www/cgi-bin/uploadsmyfile.dat
的内容)。 - 您需要调用
$cgi->param('text')
来获取正在上传的文件的名称。
这就是阻止您的程序运行的原因。您的代码的上传部分应如下所示:
my $filename = $cgi->param('text');
my $fh = $cgi->upload('text');
my $directory = '/var/www/cgi-bin/uploads';
open my $upload_fh, '>', "$directory/$filename"
or die "Can't open '$directory/$filename': $!";
print $upload_fh $_ while <$fh>;
请注意,我在此处进行了一些风格上的改进:
- 使用了
open()
的 3 参数版本
- 使用词法文件句柄
- 检查
open()
调用是否成功,如果失败则终止程序并显示一条有用的错误消息
总而言之,您似乎是从已经过时大约二十年的资源中学习 CGI 编程的。您的代码看起来像是来自 1990 年代。
其他一些提示:
- 总是
use strict
和use warnings
。 - 间接对象表示法 (
new CGI
) 可能非常混乱。请改用CGI->new
。 - 我们知道 CGI.pm 中的 HTML 生成函数自上个千年末以来就是一个糟糕的想法。请不要使用它们。 Perl 有许多优秀的模板解决方案。
- 在 2017 年编写 CGI 程序是一个糟糕的想法。查看 CGI::Alternatives 了解现代 Perl Web 开发工具的介绍。