Perlでtar.gzファイルを再帰的に展開する方法
Perlでtar.gzファイル(tgzファイル)を再帰的に展開する方法を紹介します。
1.条件
- 起動時のパラメータでトップディレクトリを指定
- トップディレクトリ配下のtar.gzファイルを展開
- 展開した中にtar.gzファイルが存在する場合はさらに展開
Perl5.8の環境です。
2.サンプルコード
拙いコードですが、1項の条件を満たすサンプルを作ってみました。
#!/usr/bin/perl
use strict;
use File::Find;
our @list;
my $dir = shift(@ARGV);
find( \&execute, $dir );
sub execute {
if (/\.tgz|\.tar\.gz/) {
my $file = "$File::Find::name";
my @grep = grep /$file/, @list if @list;
if ( !@grep ) {
push @list, $file;
my $result = `tar -zxvf $file`;
find( \&execute, $dir );
}
}
}
File::Findはディレクトリを変更しながら、すべてのファイルを処理するモジュールです。
use File::Find;
File::Find::find()は、第1パラメータに設定した関数で第2パラメータに指定したディレクトリまたはファイル(配列も可)を処理します。この1行で、第2パラメータに指定したディレクトリ配下のディレクトリやファイルをすべて探索してくれます。
find( \&execute, $dir );
execute()メソッドでは、ファイルの拡張子が「.tgz」または「.tar.gz」の場合のみ処理を継続するようにします。
if (/\.tgz$|\.tar\.gz/) {
:
}
$File::Find::nameでファイル名(フルパス)を取得します。
my $file = "$File::Find::name";
一度展開したアーカイブを展開しないよう、リストを検索します。
my @grep = grep /$file/, @list if @list;
リストになければ現在のファイルをリストに追加し、tarコマンドを実行します。
if ( !@grep ) {
push @list, $file;
my $result = `tar -zxvf $file`;
展開したらfind()を再帰的に呼び出します(呼び出さないと展開したディレクトリを探索しないのでこのようにしています)。
find( \&execute, $dir );
再帰呼び出しの第2パラメータは起動時のディレクトリを再指定していますが、本来は展開したアーカイブに含まれるディレクトリに絞った方がいいと思います。
Archive::Extractとか、もっといい方法があればどこかでつぶやいてください。
Posted by yujiro このページの先頭に戻る
- Perlでansibleライブラリを作成する方法
- perlのCPANモジュールからRPMを作成する方法
- Perlで「Subroutine permission redefined at~」を抑止する方法
- XML::Simpleのインストールでエラーになる場合の対処
- YAML::Tinyで「YAML::Tiny found bad indenting in line~」というエラーになる場合の対処
- Perlの正規表現を使って文字列をまとめて取得する方法
- Perlのハッシュでキーの有無を調べる方法
- perlで配列の途中の要素を削除する方法
- YAML::Tinyでコロンを利用する方法
- Perlで改行コードがCRのファイルを読み込む方法
- Perlで「Possible precedence issue with control flow operator」という警告の対処
- PerlのLWPで「Can't verify SSL peers without knowing which Certificate Authorities to trust」というエラーになったときの対処
- Perl+Windowsでファイルを再帰的にリネームする方法
- Perlプログラムの中でファイルの一部を書き換える方法
- Perlの「Bareword "%s" not allowed while "strict subs" in use~」というエラーについて
トラックバックURL
コメントする
greeting