使用纯 Perl 获取 blob 上传的数据
Get blob uploaded data with pure Perl
在 Javascript 中,我通过以下代码使用 XHR 发送一个 blob:
var v=new FormData();
v.append("EFD",new Blob([...Uint8Array...]));
var h=new XMLHttpRequest();
h.setRequestHeader("Content-type","multipart/form-data; charset=utf-8");
h.open("POST","...url...");
h.send(v);
在服务器中,我在 Perl 中创建了以下函数,假设实现 CGI->param
和 CGI->upload
:
# QS (Query String) receive in argument string for single parameter or array of many required parameters.
# If string been supplied: Return the value of the parameter or undef if missing.
# If array been supplied, a hash will be returned with keys for param names and their corresponding values.
# If the first argument is undef, then return hash with ALL available parameters.
sub QS {
my $b=$ENV{'QUERY_STRING'};
if($ENV{'REQUEST_METHOD'} eq "POST") {
read(STDIN,$b,$ENV{'CONTENT_LENGTH'}) or die "E100";
}
my $e=$_[0]; my $t=&AT($e); my $r={}; my @q=split(/&/,$b);
my %p=(); if($t eq "A") { %p=map { $_=>1 } @{$e}; }
foreach my $i(@q) {
my ($k,$s)=split(/=/,$i); $s=~tr/+//; $s=~s/%([a-fA-F0-9][a-fA-F0-9])/pack("C",hex())/eg;
if($t eq "") { $r->{$k}=$s; }
elsif($t eq "A") { if($p{$k}) { $r->{$k}=$s; } }
elsif($k eq $_[0]) { return $s; }
}
return $r;
}
# AT is a function for determining type of an object, and also a quck way to distinguish between just a string and a number.
sub AT {
if(!defined $_[0]) { return ""; } my $v=ref($_[0]);
if($v eq "") { return ($_[0]*1 eq $_[0])?"N":"S"; }
my $k={"ARRAY"=>"A","HASH"=>"H"};
return $k->{$v}||$_[0]->{_obt}||$v;
}
所以在主程序中它将被调用为:
my $EFD=&FW::QS("EFD"); # FW = The module name where QS and AT are.
当我从客户端发出 POST 时,服务器中的脚本不会弹出任何错误,也不会终止 - 它会继续 运行 和 运行和 运行.....无休止....消耗 100% CPU 时间和 100% 内存 - 没有任何解释。
不过我在脚本的开头有这些:
use strict;
use warnings;
use diagnostics;
但它仍然以这样的方式运行,我需要终止脚本才能终止它...
有谁知道我做错了什么...?据我所知,这里没有无限循环...如果我将 Blob 更改为“...url...?EFD=dhglkhserkhgoi”的常规经典方式,那么它就可以正常工作,但我想要一个斑点....
非常感谢
此 QS
功能仅适用于具有 application/x-www-urlencoded
主体的 POST
,而您的主体不是。
在 Javascript 中,我通过以下代码使用 XHR 发送一个 blob:
var v=new FormData();
v.append("EFD",new Blob([...Uint8Array...]));
var h=new XMLHttpRequest();
h.setRequestHeader("Content-type","multipart/form-data; charset=utf-8");
h.open("POST","...url...");
h.send(v);
在服务器中,我在 Perl 中创建了以下函数,假设实现 CGI->param
和 CGI->upload
:
# QS (Query String) receive in argument string for single parameter or array of many required parameters.
# If string been supplied: Return the value of the parameter or undef if missing.
# If array been supplied, a hash will be returned with keys for param names and their corresponding values.
# If the first argument is undef, then return hash with ALL available parameters.
sub QS {
my $b=$ENV{'QUERY_STRING'};
if($ENV{'REQUEST_METHOD'} eq "POST") {
read(STDIN,$b,$ENV{'CONTENT_LENGTH'}) or die "E100";
}
my $e=$_[0]; my $t=&AT($e); my $r={}; my @q=split(/&/,$b);
my %p=(); if($t eq "A") { %p=map { $_=>1 } @{$e}; }
foreach my $i(@q) {
my ($k,$s)=split(/=/,$i); $s=~tr/+//; $s=~s/%([a-fA-F0-9][a-fA-F0-9])/pack("C",hex())/eg;
if($t eq "") { $r->{$k}=$s; }
elsif($t eq "A") { if($p{$k}) { $r->{$k}=$s; } }
elsif($k eq $_[0]) { return $s; }
}
return $r;
}
# AT is a function for determining type of an object, and also a quck way to distinguish between just a string and a number.
sub AT {
if(!defined $_[0]) { return ""; } my $v=ref($_[0]);
if($v eq "") { return ($_[0]*1 eq $_[0])?"N":"S"; }
my $k={"ARRAY"=>"A","HASH"=>"H"};
return $k->{$v}||$_[0]->{_obt}||$v;
}
所以在主程序中它将被调用为:
my $EFD=&FW::QS("EFD"); # FW = The module name where QS and AT are.
当我从客户端发出 POST 时,服务器中的脚本不会弹出任何错误,也不会终止 - 它会继续 运行 和 运行和 运行.....无休止....消耗 100% CPU 时间和 100% 内存 - 没有任何解释。
不过我在脚本的开头有这些:
use strict;
use warnings;
use diagnostics;
但它仍然以这样的方式运行,我需要终止脚本才能终止它...
有谁知道我做错了什么...?据我所知,这里没有无限循环...如果我将 Blob 更改为“...url...?EFD=dhglkhserkhgoi”的常规经典方式,那么它就可以正常工作,但我想要一个斑点....
非常感谢
此 QS
功能仅适用于具有 application/x-www-urlencoded
主体的 POST
,而您的主体不是。