何度か、 があるとします。a.zip
これはそれ自体に解凍されますa/*
。
ただし、多くの場合、すべての内容が現在のディレクトリに漏れてしまう zip ファイルがあります。この場合、手動でディレクトリを作成しa
、そこに解凍する必要があります。
しかし、ポリシーとして常にディレクトリを作成し、zip が最初の種類であることが判明した場合、構造は次のようになり、a/a/*
理想的ではありません。
上記で説明した 2 つのタイプのうち、タイプに関係なくa.zip
解凍する方法はありますか?a/*
答え1
これを試して:
archive="archive.zip"
has_parent=$(unzip -l "$archive" | tail -n+4 | head -n-2 | awk '{split($NF,a,"/");print a[1]}' | sort -u | wc -l)
if test "$has_parent" -eq 1; then
unzip $archive
else
dir="./$(basename ${archive%%.zip})"
mkdir "$dir"
unzip -d "$dir" $archive
fi
使用する場合、次のように行zipinfo
を絞ります$has_parent
。
has_parent=$(zipinfo -1 "$archive" | awk '{split($NF,a,"/");print a[1]}' | sort -u | wc -l)
アイデアはシンプルです。アーカイブのルート レベルに複数のファイルがある場合、解凍すると現在のディレクトリが破壊されるのは明らかです。そのため、事前に親ディレクトリを作成し、そこにファイルを解凍する必要があります。そうでない場合、アーカイブ内のすべてのファイルの親が同じであれば、現在のディレクトリで解凍しても問題ありません。
答え2
zipinfo
表示、zip コンテンツに使用します。
$ zipinfo -1 a.zip
ただし、自動化の回答を探している場合、これはおそらく質問への回答にはなりません。
編集:出力の各行にスラッシュ文字があるかどうかをチェックすることができますzipinfo
。スラッシュ文字がない行があれば、その行が zip ファイルのルートにあることがわかります。
残念ながら、これをどうやって実行すればいいのか、すぐには思いつきません。うまくいくかどうかはわかりませんが、テストされていないコマンドを次に示します。
$ MKROOT=0
$ for X in $(zipinfo -1 a.zip); do $(echo "${X}" | grep "/"); if test "$?" -gt "0"; then MKROOT=1; fi; done
$ if test "${MKROOT}" -gt "0"; then mkdir "a"; cd "a"; unzip "../a.zip"; else unzip "a.zip"; fi
編集:Mark Perryman の提案の方がおそらく良いでしょう。私のコマンドはファイルがサブフォルダーに含まれているかどうかをチェックしますが、すべてが同じルートフォルダーの下にあるかどうかはチェックしないことに気づきました。