Windowsは通常、ファイル名はロケールに応じて符号化する全てのアクセント
おかげで私のフォルダを解凍するための解決策はあります。たとえば、ロシアの設定では、通常、CP866のファイル名をエンコードします。ファイル名は、同じロケール、つまりアーカイブが作成されたシステムに応じてロケールでZipに入れられます。
私は何年か前tried to solve this problemエンコーディング
の検出、およびIは、一般的にエンコーディング確実を検出する方法がないという結論に達しました。 PHPでは、あなたはZipArchive
とmb_detect_encoding
で試すことができます。
$zip = new ZipArchive;
$filename = $argv[1];
if (! $zip->open($filename))
die("failed to open $filename\n");
for ($i = 0; $i < $zip->numFiles; ++$i) {
$encoding = mb_detect_encoding($zip->getNameIndex($i), 'auto');
if (! $encoding) {
trigger_error("Failed to detect encoding for " . $zip->getNameIndex($i), E_USER_ERROR);
exit(1);
}
$zip->renameIndex($i, iconv($encoding, 'UTF-8', $zip->getNameIndex($i)));
}
$zip->extractTo('/home/ruslan/tmp/unzippped/');
$zip->close();
しかし、私の経験から、mb_detect_encoding
は非常に正確ではありません。
あなたは次のようにenca
ツールでエンコーディングを検出しようとすることができます:
ru
は言語コードです
ls -1 folder | enca -L ru
(すべての言語コードがenca --list languages
から入手できます)を。しかし、それはあなたが言語を推測する必要があります。実際にはUTF-8に1つのエンコーディングからファイル名を変換するには、あなたがもう一度、enconv
、例えば:
ls -1 folder | enconv -L russian -x UTF-8
を使用することができますが、あなたは言語を推測する必要があります。
上記のいずれかの方法でエンコーディングを検出し、使用可能なすべてのエンコーディングのリストからエンコーディングを選択するようにお勧めします。デフォルトでは、自動検出されたエンコーディングがリストで選択されている可能性があります。個人的には、スマートな自動検出機能を使用せずにエンコーディングを選択できるようにしました。
あなたがソースのエンコーディングを知っているとき
解凍が-p
オプションでパイプストリーミングをサポートしています。しかし、それはバルクデータのためだけに機能します。つまり、圧縮されていないすべてのコンテンツをプログラムに渡すファイルにストリームを分割しません。
unzip -p foo | more => foo.zipの内容をパイプ経由でプログラムに送信more
生ストリームを解析することは明らかに難しい作業です。
$path = $argv[1];
$from_encoding = isset($argv[2]) ? $argv[2] : 'CP866';
if ($handle = opendir($path)) {
while ($file = readdir($handle)) {
rename($file, iconv($from_encoding, 'UTF-8', $file));
}
closedir($handle);
}
使用例:
を別の方法として、次のようにZipArchive
を使用する一つの方法は、ディレクトリにファイルを抽出し、このようなスクリプトを含むファイル名を変換することです。
$zip = new ZipArchive;
$filename = $argv[1];
$from_encoding = isset($argv[2]) ? $argv[2] : 'CP866';
$zip->open($filename) or die "failed to open $filename\n";
for ($i = 0; $i < $zip->numFiles; ++$i) {
$zip->renameIndex($i, iconv($from_encoding,'UTF-8', $zip->getNameIndex($i)));
}
$zip->extractTo('/target/directory/');
$zip->close();
使用例:
php script.php file.zip Windows-1252
あなたは何とかファイルを共有することはできますか?私はそれを修正する方法を知っていると思いますが、答えを投稿する前に解決策をチェックしたいと思います。 –
アクセント付きのフォルダをWindows上に作成して(ファイルの有無を問わず)、winrarまたは7zipで圧縮します。ファイルは特定ではありません。 – Remi
問題は、Zip内のファイル名のエンコーディングがシステムロケールによって異なることです。 Windowsの設定によって結果が異なる場合があります。問題をすぐに解決したい場合は、ファイルを共有してください。 –