Docker容器化高可用架构部署方案(八)

07-PHP服务配置详解

本文档详细介绍PHP服务的配置,采用双容器架构(nginx:alpine + php:8.2-fpm-alpine),实现静态文件服务和动态PHP处理分离。

双容器架构说明

PHP服务由两个容器组成:

复制代码
┌─────────────────────────────────────────────────────────┐
│                    PHP服务 (双容器)                      │
├─────────────────────────────────────────────────────────┤
│                                                         │
│  ┌───────────────────┐    ┌───────────────────────────┐ │
│  │   php (nginx:alpine)│    │  php-fpm (php:8.2-fpm)   │ │
│  │   172.20.2.11      │    │  172.20.2.21              │ │
│  │                    │    │                           │ │
│  │   监听: 80         │◄───│  fastcgi_pass             │ │
│  │                    │    │  监听: 9000               │ │
│  │   静态文件         │    │  PHP解析                  │ │
│  └───────────────────┘    └───────────────────────────┘ │
│                                                         │
│              shared volume: web-data                    │
│              (/usr/share/nginx/html = /var/www/html)   │
└─────────────────────────────────────────────────────────┘

容器职责

容器 镜像 IP 职责
php nginx:alpine 172.20.2.11 静态文件服务、接收请求、转发PHP到fastcgi
php-fpm php:8.2-fpm-alpine 172.20.2.21 解析PHP代码、执行逻辑

通信流程

复制代码
客户端请求 → nginx-lb → php(172.20.2.11:80) 
                          │
                          ▼ fastcgi_pass
                    php-fpm(172.20.2.21:9000)
                          │
                          ▼ 读取/写入
                    共享卷 web-data

nginx配置(php-node*.conf)

php-node1.conf

复制代码
user nginx;
worker_processes auto;
error_log /var/log/nginx/error.log warn;
pid /var/run/nginx.pid;
​
events {
    worker_connections 1024;
    use epoll;
    multi_accept on;
}
​
http {
    include /etc/nginx/mime.types;
    default_type application/octet-stream;
​
    log_format main '$remote_addr - $remote_user [$time_local] "$request" '
                    '$status $body_bytes_sent "$http_referer" '
                    '"$http_user_agent" "$http_x_forwarded_for" '
                    'request_time: $request_time';
​
    access_log /var/log/nginx/access.log main;
​
    sendfile on;
    tcp_nopush on;
    tcp_nodelay on;
    keepalive_timeout 65;
    types_hash_max_size 2048;
    client_max_body_size 100M;
​
    gzip on;
    gzip_vary on;
    gzip_proxied any;
    gzip_comp_level 6;
    gzip_types text/plain text/css text/xml text/javascript 
               application/json application/javascript application/xml+rss 
               application/rss+xml font/truetype font/opentype 
               application/vnd.ms-fontobject image/svg+xml;
​
    server {
        listen 80;
        server_name localhost;
        root /usr/share/nginx/html;
        index index.php index.html index.htm;
​
        location / {
            try_files $uri $uri/ /index.php?$query_string;
        }
​
        location ~ \.php$ {
            fastcgi_pass 172.20.2.21:9000;
            fastcgi_index index.php;
            fastcgi_param SCRIPT_FILENAME /var/www/html$fastcgi_script_name;
            include fastcgi_params;
        }
​
        location /health {
            access_log off;
            return 200 "php-healthy\n";
            add_header Content-Type text/plain;
        }
​
        error_page 404 /404.html;
        error_page 500 502 503 504 /50x.html;
    }
}

节点配置差异

节点 配置文件 fastcgi_pass root
Node1 php-node1.conf 172.20.2.21:9000 /usr/share/nginx/html
Node2 php-node2.conf 172.20.2.22:9000 /usr/share/nginx/html
Node3 php-node3.conf 172.20.2.23:9000 /usr/share/nginx/html

关键配置项详解

1. fastcgi_pass

复制代码
location ~ \.php$ {
    fastcgi_pass 172.20.2.21:9000;  # 指向本节点的php-fpm容器
    ...
}

重要

  • 不能使用127.0.0.1:9000localhost:9000

  • 必须使用php-fpm的外部IP(macvlan分配的IP)

  • 每个节点的php.conf中IP不同

2. root路径

复制代码
root /usr/share/nginx/html;  # nginx容器内路径

注意

  • nginx容器使用/usr/share/nginx/html

  • php-fpm容器使用/var/www/html

  • 通过共享卷web-data保持一致

3. SCRIPT_FILENAME

复制代码
fastcgi_param SCRIPT_FILENAME /var/www/html$fastcgi_script_name;

说明

  • 必须是nginx容器内的完整路径

  • 与root配置保持一致

php.ini配置

复制代码
[PHP]
upload_max_filesize = 50M
post_max_size = 50M
max_execution_time = 60
memory_limit = 256M
display_errors = Off
log_errors = On
error_log = /var/log/php/error.log
date.timezone = Asia/Shanghai
​
[Session]
session.save_handler = redis
session.save_path = "tcp://172.20.3.11:6379?auth=YourStr0ng!Pass"
​
[opcache]
opcache.enable = 1
opcache.memory_consumption = 128
opcache.interned_strings_buffer = 8
opcache.max_accelerated_files = 4000

配置项说明

配置 说明
upload_max_filesize 上传文件最大大小
post_max_size POST数据最大大小
max_execution_time 脚本最大执行时间
memory_limit 脚本最大内存
session.save_handler Session存储方式
session.save_path Redis服务器地址
opcache.* OPcache加速配置

Docker Compose配置

Node1示例

复制代码
php:
  image: nginx:alpine
  container_name: php
  networks:
    backend-net:
      ipv4_address: 172.20.2.11
  volumes:
    - ./config/php/php-node1.conf:/etc/nginx/nginx.conf:ro
    - web-data:/usr/share/nginx/html
  restart: unless-stopped
  healthcheck:
    test: ["CMD-SHELL", "curl -f http://localhost/index.php > /dev/null 2>&1 || exit 1"]
    interval: 10s
    timeout: 5s
    retries: 3
​
php-fpm:
  build: ./config/php-fpm  # 基于php:8.2-fpm-alpine安装pdo_mysql
  container_name: php-fpm
  networks:
    backend-net:
      ipv4_address: 172.20.2.21
  volumes:
    - ./config/php/php.ini:/usr/local/etc/php/conf.d/custom.ini:ro
    - web-data:/var/www/html
  restart: unless-stopped
  healthcheck:
    test: ["CMD", "php-fpm", "-t"]
    interval: 10s
    timeout: 5s
    retries: 3
​
volumes:
  web-data:

服务IP分配

节点 php php-fpm
Node1 172.20.2.11 172.20.2.21
Node2 172.20.2.12 172.20.2.22
Node3 172.20.2.13 172.20.2.23

部署注意事项

1. 配置文件必须先创建

复制代码
# 确保配置文件存在
touch /opt/cluster-deploy/config/php/php-node1.conf
touch /opt/cluster-deploy/config/php/php-node2.conf
touch /opt/cluster-deploy/config/php/php-node3.conf
touch /opt/cluster-deploy/config/php/php.ini

2. 正确配置fastcgi_pass

  • Node1: fastcgi_pass 172.20.2.21:9000;

  • Node2: fastcgi_pass 172.20.2.22:9000;

  • Node3: fastcgi_pass 172.20.2.23:9000;

3. 共享卷一致性

  • nginx容器挂载:web-data:/usr/share/nginx/html

  • php-fpm容器挂载:web-data:/var/www/html

  • 确保两边路径对应正确

4. 健康检查端点

每个php容器提供/health端点:

复制代码
# 测试健康状态
curl http://172.20.2.11/health
curl http://172.20.2.12/health
curl http://172.20.2.13/health

创建测试页面

复制代码
# 创建测试页面
cat > /opt/cluster-deploy/index.php << 'EOF'
<?php
echo "<h1>PHP Service Test</h1>";
echo "<p>Server: " . gethostname() . "</p>";
echo "<p>PHP Version: " . phpversion() . "</p>";
echo "<p>Time: " . date('Y-m-d H:i:s') . "</p>";
echo "<p>REMOTE_ADDR: " . $_SERVER['REMOTE_ADDR'] . "</p>";

# 测试Redis连接
try {
    $redis = new Redis();
    $redis->connect('172.20.3.11', 6379);
    $redis->auth('YourStr0ng!Pass');
    echo "<p>Redis: Connected</p>";
} catch (Exception $e) {
    echo "<p>Redis: Error - " . $e->getMessage() . "</p>";
}

# 测试Session
session_start();
$_SESSION['test'] = 'Hello from PHP!';
echo "<p>Session ID: " . session_id() . "</p>";
echo "<p>Session Data: " . ($_SESSION['test'] ?? 'Not set') . "</p>";
?>
EOF

# 复制到共享卷
docker run --rm -v web-data:/data -v $(pwd)/index.php:/index.php alpine cp /index.php /data/

常见问题

Q1: 502 Bad Gateway

  • 检查php-fpm是否运行:docker ps | grep php-fpm

  • 检查fastcgi_pass地址是否正确

  • 检查网络连通性:ping 172.20.2.21

Q2: PHP代码不执行

  • 检查SCRIPT_FILENAME路径

  • 确认root路径与挂载路径一致

Q3: Session无法写入Redis

  • 检查Redis连接:telnet 172.20.3.11 6379

  • 验证密码认证

  • 检查php.ini中的session配置

验证命令

复制代码
# 查看PHP容器
docker ps | grep -E "php|php-fpm"

# 测试PHP服务
curl http://172.20.2.11/index.php
curl http://172.20.2.12/index.php
curl http://172.20.2.13/index.php

# 测试健康检查
curl http://172.20.2.11/health
curl http://172.20.2.12/health
curl http://172.20.2.13/health

# 查看PHP-FPM日志
docker logs php-fpm

# 查看PHP版本
docker exec php-fpm php -v

下一步

相关推荐
倔强的石头1062 小时前
异构操作系统架构下的数据库表空间高级管理:路径兼容与自动化运维实战
运维·数据库·架构
阿洛学长2 小时前
使用 Hexo+GitHub 搭建个人免费博客教程(小白)
运维·数据库·架构
刘某的Cloud2 小时前
docker && containerd 镜像加速
运维·docker·容器·containerd·镜像加速
恋猫de小郭2 小时前
2026 Android I/O ,全新 AI 手机、 Android PC 和自动驾驶
android·人工智能·智能手机
2301_780789662 小时前
容器环境漏洞扫描:适配 K8s 架构的镜像与 Pod 安全检测方案
网络·安全·web安全·云原生·架构·kubernetes·ddos
庞轩px2 小时前
第一篇:RocketMQ架构与核心概念——一条消息从生产到消费的完整旅程
架构·rocketmq
前端若水2 小时前
开发环境准备:Python、Node.js、Docker与Git
python·docker·node.js
三产2 小时前
Hermes 教程 03:Skills 系统
android·java·数据库
AI玫瑰助手2 小时前
Python流程控制:for循环遍历字符串列表字典
android·java·python