Docker构建PHP容器时无法写入php.ini的问题咨询
问题场景
使用php:8.2-fpm-alpine镜像构建PHP容器时,构建过程无致命错误,所有添加的PHP扩展均已正常加载(显示Additional .ini files parsed),但构建输出中多次出现如下错误提示:
cannot open php.ini "/usr/local/etc/php" for writing You should add "extension=imagick.so" to php.ini
已尝试复制/usr/local/etc/php/php.ini-development到/usr/local/etc/php/php.ini,甚至修改文件所属用户为docker,问题仍存在。想确认该错误是否可忽略,或有无修复方法。
构建日志
#10 71.97 Build process completed successfully #10 71.97 Installing '/usr/local/lib/php/extensions/no-debug-non-zts-20220829/xdebug.so' #10 71.98 install ok: channel://pecl.php.net/xdebug-3.2.0 #10 71.98 cannot open php.ini "/usr/local/etc/php" for writing #10 71.98 You should add "extension=imagick.so" to php.ini #10 71.98 cannot open php.ini "/usr/local/etc/php" for writing #10 71.98 You should add "extension=imagick.so" to php.ini #10 71.98 cannot open php.ini "/usr/local/etc/php" for writing #10 71.98 You should add "extension=redis.so" to php.ini #10 71.98 cannot open php.ini "/usr/local/etc/php" for writing #10 71.98 You should add "extension=imagick.so" to php.ini #10 71.98 cannot open php.ini "/usr/local/etc/php" for writing #10 71.98 You should add "extension=redis.so" to php.ini #10 71.98 cannot open php.ini "/usr/local/etc/php" for writing #10 71.98 You should add "extension=memcached.so" to php.ini #10 71.98 cannot open php.ini "/usr/local/etc/php" for writing #10 71.98 You should add "zend_extension=/usr/local/lib/php/extensions/no-debug-non-zts-20220829/xdebug.so" to php.ini #10 71.98 cannot open php.ini "/usr/local/etc/php" for writing #10 71.98 You should add "zend_extension=/usr/local/lib/php/extensions/no-debug-non-zts-20220829/xdebug.so" to php.ini #10 71.98 cannot open php.ini "/usr/local/etc/php" for writing #10 71.98 You should add "zend_extension=/usr/local/lib/php/extensions/no-debug-non-zts-20220829/xdebug.so" to php.ini #10 71.98 cannot open php.ini "/usr/local/etc/php" for writing #10 71.98 You should add "zend_extension=/usr/local/lib/php/extensions/no-debug-non-zts-20220829/xdebug.so" to php.ini #10 72.05 fetch https://dl-cdn.alpinelinux.org/alpine/v3.17/main/x86_64/APKINDEX.tar.gz #10 72.32 fetch https://dl-cdn.alpinelinux.org/alpine/v3.17/community/x86_64/APKINDEX.tar.gz #10 72.54 (1/1) Installing .docker-php-ext-enable-deps (20230202.070642) #10 72.55 OK: 459 MiB in 136 packages #10 72.84 (1/1) Purging .docker-php-ext-enable-deps (20230202.070642) #10 72.84 OK: 459 MiB in 135 packages
原Dockerfile
FROM php:8.2-fpm-alpine RUN pear config-set php_ini "$PHP_INI_DIR" RUN apk update && apk upgrade && apk add --no-cache $PHPIZE_DEPS libzip-dev zlib-dev gmp-dev libmemcached-dev linux-headers imagemagick-dev libpng-dev libwebp-dev libjpeg-turbo-dev freetype-dev \ && docker-php-ext-configure gd --enable-gd --with-freetype --with-jpeg --with-webp \ && docker-php-ext-install gd gmp pdo_mysql opcache zip # 我试过添加这行,但还是出现同样的错误 # 此时php.ini在容器中属于root用户 # 如果创建docker用户并让其拥有该文件,还是会出现同样的错误 RUN cp /usr/local/etc/php/php.ini-development /usr/local/etc/php/php.ini RUN pecl install imagick redis memcached xdebug \ && docker-php-ext-enable imagick redis memcached xdebug COPY ./xdebug/xdebug.ini /usr/local/etc/php/conf.d/docker-php-ext-xdebug.ini COPY --from=composer:latest /usr/bin/composer /usr/bin/composer RUN addgroup -g 1000 docker && adduser -D -u 1000 -G docker -s /bin/sh docker USER docker
问题分析
错误的核心原因是:pear config-set php_ini "$PHP_INI_DIR"这行命令将pecl的php.ini配置指向了目录/usr/local/etc/php,而pecl需要的是具体的php.ini文件路径。当pecl安装扩展后尝试自动写入扩展配置到php.ini时,发现目标是目录而非文件,因此抛出“无法打开php.ini进行写入”的错误。
另外,docker-php-ext-enable工具会自动在/usr/local/etc/php/conf.d/目录下生成单独的扩展配置文件,不需要手动修改主php.ini,所以构建日志中“应添加xxx到php.ini”的提示其实是多余的,扩展已经通过conf.d的配置正常加载。
修复方法
1. 修正pecl的php.ini配置
将pecl的php_ini配置指向具体的php.ini文件,同时调整命令顺序,先复制php.ini再设置pecl配置:
修改后的Dockerfile:
FROM php:8.2-fpm-alpine RUN apk update && apk upgrade && apk add --no-cache $PHPIZE_DEPS libzip-dev zlib-dev gmp-dev libmemcached-dev linux-headers imagemagick-dev libpng-dev libwebp-dev libjpeg-turbo-dev freetype-dev \ && docker-php-ext-configure gd --enable-gd --with-freetype --with-jpeg --with-webp \ && docker-php-ext-install gd gmp pdo_mysql opcache zip # 先复制php.ini到目标路径 RUN cp /usr/local/etc/php/php.ini-development /usr/local/etc/php/php.ini # 将pecl的php_ini配置指向具体的php.ini文件 RUN pear config-set php_ini "$PHP_INI_DIR/php.ini" RUN pecl install imagick redis memcached xdebug \ && docker-php-ext-enable imagick redis memcached xdebug COPY ./xdebug/xdebug.ini /usr/local/etc/php/conf.d/docker-php-ext-xdebug.ini COPY --from=composer:latest /usr/bin/composer /usr/bin/composer RUN addgroup -g 1000 docker && adduser -D -u 1000 -G docker -s /bin/sh docker USER docker
2. 错误是否可忽略?
如果不修正配置,这个错误不会影响容器的正常运行——因为扩展已经通过docker-php-ext-enable生成的conf.d配置文件正常加载。但修正配置可以消除构建过程中的错误提示,让构建日志更干净。
补充说明
- 不需要手动修改php.ini添加扩展配置,
docker-php-ext-enable会自动完成这一步,生成的配置文件在conf.d目录下,PHP启动时会自动加载这些文件。 - 切换到
docker用户的步骤放在最后即可,前面的构建操作需要root权限。
内容的提问来源于stack exchange,提问作者Cudos

