Socketに関して
SocketでURLで指定されたバナーを一旦ダウンロードし、
画像サイズを取得するプログラムなのですが、
以下のソースでは、画像が存在するURLを指定しても
「バナ-画像が存在しません。バナ-URLを確認してください。」
となってしまいます。
どこが不具合なのか分かる方がいらっしゃれば教えて頂けないでしょうか?
サーバーは「land.to」です。
use Socket;
sub GetBannerSize{
#バナ-サイズ取得(sock接続)
my ( $url ) = @_;
my ( $host, $port, $path, $dir, $file, $base, $ext, $width, $height, $ipaddr, $sockaddr, $tmpimg, $data );
$url =~ /(http:)?(\/\/)?([^:\/]*)?(:([0-9]+))?(\/.*)?/;
$host = $3;
if ($host eq "" || $host eq $ENV{'SERVER_NAME'}) {$host = 'localhost';}
$path = $6;
if ($path eq "") {$path = '/';}
if ($path =~ /(.*)\/(.*)/) {
$dir = $1.'/';
$file = $2;
} else {
$dir = './';
$file = $path;
}
if ($file =~ /(.*)\.(.*)/) {
$base = $1;
$ext = $2;
} else { # 拡張子なし
$base = $file;
$ext = "";
}
$port = getservbyname("http", "tcp");
$ipaddr = inet_aton($host) || &error("host($host) not found.");
$sockaddr = pack_sockaddr_in($port, $ipaddr);
socket(SOCK, PF_INET, SOCK_STREAM, 0) || &error("socket error.");
connect(SOCK, $sockaddr) || &error("connect $host $port error.");
select(SOCK);
$|=1;
select(STDOUT);
print SOCK << "END_OF_DOC";
GET $path HTTP/1.0
Host:$host
Connection:close
END_OF_DOC
while(<SOCK>){
last if m/^\r\n$/;
}
$tmpimg = "";
if ($ext eq "gif") {
$tmpimg = "./temp/tmp.gif";
}elsif ($ext eq "jpg" || $ext eq "jpeg") {
$tmpimg = "./temp/tmp.jpg";
}elsif ($ext eq "png") {
$tmpimg = "/temp/tmp.png";
}else{
&error("画像形式が正しくありません。");
}
open(OUT,">$tmpimg");
while (<SOCK>) {
if ($_ =~ /<HTML>/i) { &error("バナ-画像が存在しません。バナ-URLを確認してください。"); }
print OUT $_;
}
close(OUT);
close SOCK;
$width = 0;
$height = 0;
if ($ext eq "gif") {
open(IN,"$tmpimg") || return (0,0);
binmode(IN);
sysread(IN,$data,10);
close(IN);
if ($data =~ /^GIF/) { $data = substr($data,-4); }
$width = unpack("v",substr($data,0,2));
$height = unpack("v",substr($data,2,2));
} elsif ($ext eq "jpg" || $ext eq "jpeg") {
local($t, $m, $c, $l);
open(IN,"$tmpimg") || return (0,0);
binmode(IN);
read(IN, $t, 2);
while (1) {
read(IN, $t, 4);
($m, $c, $l) = unpack("a a n", $t);
if ($m ne "\xFF") { $W = $H = 0; last; }
elsif ((ord($c) >= 0xC0) && (ord($c) <= 0xC3)) {
read(IN, $t, 5);
($height, $width) = unpack("xnn", $t);
last;
}
else {
read(IN, $t, ($l - 2));
}
}
close(IN);
} elsif ($ext eq "png") {
open(IN,"$tmpimg") || return (0,0);
binmode(IN);
read(IN, $data, 24);
close(IN);
$width = unpack("N", substr($data, 16, 20));
$height = unpack("N", substr($data, 20, 24));
}
unlink $tmpimg;
return( $width, $height );
}
お礼
てっきり文字化けかと思っていました。 自分の知識不足でした。 Transfer-Encoding: chunkedに関して調べなおしてがんばって実装してみたいと思います。 ご回答ありがとうございました。