Windowsで作ったZIPファイルはファイル名がSJISであり、これをLinuxのPHPでファイル名をUTF-8にして解凍したい。 という話
blog.narazaki.info
PHPでZipArchiveを使うと、statIndex() が勝手に憶測で文字コード変換をするために文字コードが破壊されてしまうバグがあるという話。
PHP7なら第2引数に ZipArchive::FL_ENC_RAW を指定することで勝手な変換を抑止できるが、これは PHP 7.0.8 以降で利用可能 であり、当然 PHP5.6 には定義が無い。
で、万策尽きたかと思ってたけど、どうも5.6でも機能はあるらしい。
ZipArchive::FL_ENC_RAW、「PHP 7.0.8 以降で利用可能です。」って書かれてるけど5.6.33でも動いてる??むしろ使わないと日本語ファイル名まともに展開できないぞ。。
— kojima (@kjm0213) 2018年1月12日
そこで 定数 ZipArchive::FL_ENC_RAW の代わりに 64 を指定したら なんと期待通りに動作してしまった。 やったぜ
<? function unzip($zipfile, $dir) { $zip = new ZipArchive; $index = 0; while($entry = $zip->statIndex($index, 64)) { // ZipArchive::FL_ENC_RAW = 64 $sjisname = $entry['name']; $utf8name = mb_convert_encoding($sjisname, "UTF-8", "CP932"); $zip->renameIndex($index, $utf8name); $zip->extractTo($dir, $utf8name); $index++; } $zip->close(); return; }