如何合并Nginx与PHP-FPM的Dockerfile实现单镜像多阶段构建
将PHP-FPM与Nginx合并为单个Docker镜像的解决方案
你当前的Dockerfile采用多阶段构建,但第二个Nginx阶段完全没有继承第一个PHP-FPM阶段的内容——最终生成的镜像只有Nginx环境,没有PHP-FPM进程,因此无法解析PHP文件,只会将其当作静态资源直接下载。
调整后的完整Dockerfile
# 第一阶段:构建PHP-FPM环境,命名为builder FROM --platform=linux/amd64 php:8.1-fpm AS builder # 安装所需PHP扩展 RUN docker-php-ext-install pdo_mysql # 可选:添加其他扩展,例如gd、redis # RUN docker-php-ext-install gd && pecl install redis && docker-php-ext-enable redis # 第二阶段:基于Nginx镜像整合PHP-FPM FROM --platform=linux/amd64 nginx # 从builder阶段复制PHP-FPM核心组件 COPY --from=builder /usr/local/etc/php/ /usr/local/etc/php/ COPY --from=builder /usr/local/sbin/php-fpm /usr/local/sbin/php-fpm COPY --from=builder /usr/local/lib/php/ /usr/local/lib/php/ COPY --from=builder /var/www/html/ /var/www/html/ # 复制项目代码与Nginx配置 ADD src/public /usr/share/nginx/html/public ADD conf/nginx.conf /etc/nginx/conf.d/default.conf # 安装supervisord用于管理多进程 RUN apt-get update && apt-get install -y --no-install-recommends supervisor \ && rm -rf /var/lib/apt/lists/* # 添加supervisord配置文件 ADD conf/supervisord.conf /etc/supervisor/conf.d/supervisord.conf # 设置容器启动命令 CMD ["/usr/bin/supervisord", "-c", "/etc/supervisor/conf.d/supervisord.conf"]
配套的supervisord配置文件(conf/supervisord.conf)
[supervisord] nodaemon=true [program:php-fpm] command=/usr/local/sbin/php-fpm autostart=true autorestart=true stdout_logfile=/dev/stdout stdout_logfile_maxbytes=0 stderr_logfile=/dev/stderr stderr_logfile_maxbytes=0 [program:nginx] command=/usr/sbin/nginx -g "daemon off;" autostart=true autorestart=true stdout_logfile=/dev/stdout stdout_logfile_maxbytes=0 stderr_logfile=/dev/stderr stderr_logfile_maxbytes=0
关键调整说明
- 多阶段内容复制:通过
COPY --from=builder将第一个阶段的PHP-FPM二进制文件、配置文件、PHP库文件复制到Nginx镜像中,确保容器内具备PHP解析能力。 - 多进程管理:单容器默认只能启动一个主进程,因此使用
supervisord同时启动并监控Nginx和PHP-FPM两个服务,避免其中一个进程退出导致容器停止。 - Nginx配置无需修改:你原有的Nginx配置中
fastcgi_pass 127.0.0.1:9000配置正确,因为PHP-FPM会在容器内部的9000端口监听请求。
构建与运行命令
# 构建镜像 docker build -t php-nginx-app . # 启动容器 docker run -p 80:80 php-nginx-app
内容的提问来源于stack exchange,提问作者andreas
相关产品推荐
相关产品推荐

