PHP7.1 で zip圧縮するのにハマったメモ


こんにちは。
開発チームのワイルド担当、まんだいです。

PHP7.1 環境で開発をしているコンテンツで、PHP で zip 圧縮を行うコードを書いてもらいました。
マージして確認ができればリリース、と行きたかったのですが、少し手間取ったので解決法を共有したいと思います。

ZipArchive がないというエラーから始まった

マージして実行すると、以下のようなエラーが出ました。

Error - Class 'ZipArchive' not found in APPPATH/classes/logic/monitoring.php on line 721

 

もちろんこれはモジュールのインストールを行っていなかったから発生したものなので、インストールを試みます。

今インストールされている PHP 関連のモジュールは以下の通り。

$ yum list installed | grep php
php.x86_64                           7.1.22-1.el7.remi              @remi-php71
php-cli.x86_64                       7.1.22-1.el7.remi              @remi-php71
php-common.x86_64                    7.1.22-1.el7.remi              @remi-php71
php-devel.x86_64                     7.1.22-1.el7.remi              @remi-php71
php-fpm.x86_64                       7.1.22-1.el7.remi              @remi-php71
php-gd.x86_64                        7.1.22-1.el7.remi              @remi-php71
php-json.x86_64                      7.1.22-1.el7.remi              @remi-php71
php-mbstring.x86_64                  7.1.22-1.el7.remi              @remi-php71
php-mcrypt.x86_64                    7.1.22-1.el7.remi              @remi-php71
php-mysqlnd.x86_64                   7.1.22-1.el7.remi              @remi-php71
php-pdo.x86_64                       7.1.22-1.el7.remi              @remi-php71
php-pecl-imagick.x86_64              3.4.3-8.el7.remi.7.1           @remi-php71
php-xml.x86_64                       7.1.22-1.el7.remi              @remi-php71

 

たしかにない。
PHP が読み込んでいるモジュールを確認してみます。

$ php -m
[PHP Modules]
bz2
calendar
Core
ctype
curl
date
dom
exif
fileinfo
filter
ftp
gd
gettext
hash
iconv
imagick
json
libxml
mbstring
mcrypt
mysqli
mysqlnd
openssl
pcntl
pcre
PDO
pdo_mysql
pdo_sqlite
Phar
readline
Reflection
session
SimpleXML
sockets
SPL
sqlite3
standard
tokenizer
wddx
xml
xmlreader
xmlwriter
xsl
# このへんにあるはず
zlib

 

ありませんね。
ということで、 yum を使ってサクッとインストールしていましょう。

 

yum を使って php-pecl-zip をインストールしてみる

PHP は yum で用意したものなので、今回も yum でインストールしていきます。

$ yum install –enablerepo=remi-php71 php-pecl-zip
Loaded plugins: fastestmirror
Loading mirror speeds from cached hostfile
 * base: ftp.jaist.ac.jp
 * epel: mirrors.kernel.org
 * extras: ftp.jaist.ac.jp
 * remi-safe: ftp.riken.jp
 * updates: ftp.jaist.ac.jp
Package matching php-common-5.4.16-45.el7.x86_64 already installed. Checking for update.

 

変な怒られ方をしましたね。
利用している PHP のバージョンは 7.1 ですから、 php-common-5.4 が原因でインストールできないというのはおかしな話です。

PECL のモジュールなので、直接コンパイルしてみるとしましょう。

 

PECL モジュールをコンパイルしてみる

ソースはPECL :: Package :: zipからダウンロードしました。

$ phpize
Configuring for:
PHP Api Version:         20160303
Zend Module Api No:      20160303
Zend Extension Api No:   320160303

$ ./configure
checking for grep that handles long lines and -e... /bin/grep
checking for egrep... /bin/grep -E
checking for a sed that does not truncate output... /bin/sed
checking for cc... cc
checking whether the C compiler works... yes
checking for C compiler default output file name... a.out
checking for suffix of executables...
checking whether we are cross compiling... no
checking for suffix of object files... o
checking whether we are using the GNU C compiler... yes
checking whether cc accepts -g... yes
checking for cc option to accept ISO C89... none needed
checking how to run the C preprocessor... cc -E
checking for icc... no
checking for suncc... no
checking whether cc understands -c and -o together... yes
checking for system library directory... lib
checking if compiler supports -R... no
checking if compiler supports -Wl,-rpath,... yes
checking build system type... x86_64-unknown-linux-gnu
checking host system type... x86_64-unknown-linux-gnu
checking target system type... x86_64-unknown-linux-gnu
checking for PHP prefix... /usr
checking for PHP includes... -I/usr/include/php -I/usr/include/php/main -I/usr/include/php/TSRM -I/usr/include/php/Zend -I/usr/include/php/ext -I/usr/include/php/ext/date/lib
checking for PHP extension directory... /usr/lib64/php/modules
checking for PHP installed headers prefix... /usr/include/php
checking if debug is enabled... no
checking if zts is enabled... no
checking for re2c... no
configure: WARNING: You will need re2c 0.13.4 or later if you want to regenerate PHP parsers.
checking for gawk... gawk
checking for zip archive read/writesupport... yes, shared
checking libzip... yes
checking PHP version... PHP 7.0 - 7.2
checking for pkg-config... /bin/pkg-config
checking for libzip... configure: error: system libzip must be upgraded to version >= 0.11

 

libzip のバージョンが低いということで怒られました。
libzip のバージョンを上げるという方法もありますが、色々影響が出るのも嫌なのでちょっと検索。

あまり情報がないです。
PHP のインストールに関する記事はそこそこあるのですが、 php-pecl-zip となると、途端に記事数が激減。範囲を英語に広げてもなかなかレアなケースなのかも知れません。

 

やっぱり yum じゃないか?という疑惑

ちょっと発想を変えて、原点に帰って yum の結果を見てみます。
yum でインストールした場合、 php-commom が原因でインストールが止まっていたわけですから、これをスルーさせれば何とかなるんじゃないか?と考えました。

$ yum install --enablerepo=remi-php71 php-pecl-zip --exclude=php-common

Loaded plugins: fastestmirror
Loading mirror speeds from cached hostfile
 * base: ftp.jaist.ac.jp
 * epel: mirrors.kernel.org
 * extras: ftp.jaist.ac.jp
 * remi-php71: ftp.riken.jp
 * remi-safe: ftp.riken.jp
 * updates: ftp.jaist.ac.jp
Resolving Dependencies
--> Running transaction check
---> Package php-pecl-zip.x86_64 0:1.15.3-1.el7.remi.7.1 will be installed
--> Processing Dependency: libzip5(x86-64) >= 1.5.1 for package: php-pecl-zip-1.15.3-1.el7.remi.7.1.x86_64
--> Processing Dependency: libzip.so.5()(64bit) for package: php-pecl-zip-1.15.3-1.el7.remi.7.1.x86_64
--> Running transaction check
---> Package libzip5.x86_64 0:1.5.1-1.el7.remi will be installed
--> Finished Dependency Resolution

Dependencies Resolved

===================================================================================================================
 Package                   Arch                Version                               Repository               Size
===================================================================================================================
Installing:
 php-pecl-zip              x86_64              1.15.3-1.el7.remi.7.1                 remi-php71               51 k
Installing for dependencies:
 libzip5                   x86_64              1.5.1-1.el7.remi                      remi-safe                55 k

Transaction Summary
===================================================================================================================
Install  1 Package (+1 Dependent package)

Total download size: 107 k
Installed size: 280 k
Is this ok [y/d/N]: y
Downloading packages:
(1/2): php-pecl-zip-1.15.3-1.el7.remi.7.1.x86_64.rpm                                        |  51 kB  00:00:00
(2/2): libzip5-1.5.1-1.el7.remi.x86_64.rpm                                                  |  55 kB  00:00:00
-------------------------------------------------------------------------------------------------------------------
Total                                                                              214 kB/s | 107 kB  00:00:00
Running transaction check
Running transaction test
Transaction test succeeded
Running transaction
  Installing : libzip5-1.5.1-1.el7.remi.x86_64                                                                 1/2
  Installing : php-pecl-zip-1.15.3-1.el7.remi.7.1.x86_64                                                       2/2
  Verifying  : libzip5-1.5.1-1.el7.remi.x86_64                                                                 1/2
  Verifying  : php-pecl-zip-1.15.3-1.el7.remi.7.1.x86_64                                                       2/2

Installed:
  php-pecl-zip.x86_64 0:1.15.3-1.el7.remi.7.1

Dependency Installed:
  libzip5.x86_64 0:1.5.1-1.el7.remi

Complete!

 

依存解決で新しい libzip がインストールされたようですが、無事 php-pecl-zip のインストールができました!
libzip5 という違う名前なので問題ないでしょう!

 

まとめ

CentOS では、今でも yum の標準リポジトリに登録されている PHP が5系なので、いい加減これをどうにかしてほしいところではありますが、 –exclude オプションで php-common を除外することで無駄な依存解決を発生させずにインストールすることができました。

yum はかなり優秀なので、なかなかお目にかからないケースですね。
PHP で zip圧縮を行う場合は PHP のバージョンに気をつけたほうがよいかも知れません。

以上です。


この記事をかいた人

About the author