Image::Imlib2 を使ってサーバ上の画像を一括圧縮
ブログを自宅サーバから sakuta VPS へ移行しましたが、1.5G プランなのでディスク容量は 50GB しかありません。デジタル一眼で撮った写真を今までは気兼ねなくバシバシとアップロードできていたのですが、移行した時点でディスク使用量が 30% 近くまで行ってしまいました。
# df -k Filesystem 1K-ブロック 使用 使用可 使用% マウント位置 /dev/hda2 17634636 7249188 9444844 44% / /dev/hda1 101086 11918 83949 13% /boot tmpfs 771224 0 771224 0% /dev/shm /dev/hdb1 30961664 10937264 18451640 38% /home
今後を考えると画質を見た目変わらない程度で圧縮をかけておきたいなぁ〜と思って、perl script を書きました。圧縮効率は 50% 程度といったところでしょうか。1.3GB が 530MB 程まで小さくなりました。ネットワーク効率も考えるとなかなか良い数値だと思います。
さて気になる画質の方ですが、見た目全く問題ありません。例えばファイルサイズが約 18% まで縮小できた画像を元画像(左)と変換画像(右)で比較してみます。
同じくファイルサイズが約 18% まで縮小できた別の画像を元画像(左)と変換画像(右)で比較してみます。
というわけで全く問題ないことがご確認いただけたかと思います。今回は Image::Imlib2 の品質パラメータを 95% にセッティングしましたが、圧縮率を高めたい場合には、ここの数値を下げればOKです。ご自分の要件にあわせて設定していただければと思います。
以下ソースです。あらかじめ Image::Imlib2, File::Find, File::Find::Path, File::Path をインストールしておく必要があります。
use strict;
use Image::Imlib2;
use File::Find;
use File::Find::Rule;
use File::Path;
die "Usage: perl img_compress.pl src_dir dst_dir\n" if !defined $ARGV[0] || !defined $ARGV[1];
my $src = $ARGV[0];
my $dst = $ARGV[1];
my @files = File::Find::Rule->file->in($src);
for my $file (@files) {
compress( $file, $dst );
}
sub compress {
my $file = shift;
my $dst = shift;
my $dstfile = "$dst/$file";
my $quality = 95;
my ($dstdir) = $dstfile =~ m!^(.+)/.*.*$!;
my ($suffix) = $file =~ /.+\.(.+?)$/;
return if $suffix !~ /jpeg|jpg$/;
return if $file =~ /-thumb/;
File::Path::make_path($dstdir);
eval {
my $img = Image::Imlib2->load($file);
$img = $img->create_scaled_image( $img->width, $img->height );
$img->set_quality($quality);
$img->save($dstfile);
my $src_size = -s $file;
my $dst_size = -s $dstfile;
my $per = int( 100 * $dst_size / $src_size );
print "$file\t[$src_size] -> [$dst_size]\t $per \%\n";
unlink $dstfile if $dst_size > $src_size;
};
if ($@) {
print "$file\t -> err: $@";
}
}
使い方は下記コマンドを実行して、別ディレクトリに生成される圧縮画像ファイルをご自分でご確認になった上で cp コマンド等で上書きすることを想定した作りです。なお元画像以上のサイズになってしまった変換画像は削除する動作になっているので、圧縮できた画像ファイルだけが変換先のディレクトリ内に残る仕様です。
perl img_compress.pl 変換元のディレクトリ名 変換先のディレクトリ名
Enjoy!!






コメントやシェアをお願いします!