当 php artisan serve
无法支撑百万用户时,你需要这些
基于 50+ 生产事故提炼 | 覆盖单机到云原生架构 | 附可复制代码片段
一、Laravel 专属运维灾难现场与急救方案
🚨 灾难 1:队列积压引发订单雪崩
# 紧急诊断
redis-cli --bigkeys | grep queue # 定位阻塞队列
horizon:current --quiet # 检查运行中的 Worker
根治方案:
// config/horizon.php
'environments' => [
'production' => [
'supervisor-1' => [
'connection' => 'redis',
'balance' => 'auto', # 动态负载均衡
'minProcesses' => 10, # 最低进程数
'maxProcesses' => 50, # 峰值扩容上限
'tries' => 3, # 失败重试
'timeout' => 60, # 任务超时(秒)
]
]
]
💥 灾难 2:存储目录权限引发的 500 血案
根本原因:www-data
用户无权写 storage/logs
终极防御:
# 部署脚本中加入权限锁定
sudo setfacl -R -d -m u:www-data:rwx ./storage
sudo setfacl -R -d -m u:deploy-user:rwx ./storage # 部署账户
find storage -type d -exec chmod 2775 {} \; # SETGID 保持组权限
☢️ 灾难 3:.env
配置泄露导致数据库被删
# 安全扫描(定期执行)
grep -r "DB_PASSWORD" .env
grep -r "AWS_ACCESS_KEY" ./*
安全架构升级:
graph TB
A[本地.env] -->|开发环境| B[Git忽略]
A -->|生产环境| C[Vault/Consul]
C --> D[K8s Secrets]
D --> E[Pod环境变量]
二、Laravel 运维核心六边形能力
1. 🔥 Linux 生存技能(PHP 特供版)
故障场景 | 救命命令 |
---|---|
文件句柄泄漏 | lsof -p $(pgrep php-fpm) | wc -l |
定时任务不执行 | sudo -u www-data php artisan schedule:run |
内存泄漏 | watch -n 1 'ps -o rss,cmd -C php-fpm' |
2. ⚡ PHP-FPM 调优公式
; /etc/php/8.2/fpm/pool.d/www.conf
pm = dynamic
pm.max_children = (可用内存 * 0.8) / 单进程内存
; 示例:8GB 服务器,进程消耗 80MB → max_children = (8192*0.8)/80 ≈ 82
pm.start_servers = CPU核心数 * 4
pm.process_idle_timeout = 10s # 释放闲置进程
request_terminate_timeout = 30 # 防止死请求
3. 🚦 队列系统深度运维
Horizon 监控看板关键指标:
- 队列等待时间:>60秒触发扩容
- 失败任务率:>5% 触发告警
- 内存使用:Worker 突破 100MB 需优化
# 队列故障转移方案
php artisan queue:failed-table # 创建失败记录表
php artisan queue:retry all # 批量重试
4. 🛡️ 数据库防御式编程
// 数据库操作黄金法则
DB::transaction(function () use ($request) {
$order = Order::lockForUpdate()->find($id); // 悲观锁
if ($order->status !== 'pending') {
throw new OrderConflictException;
}
$order->update([...]);
}, 3); // 重试3次
5. 🤖 零停机部署流水线
# GitHub Actions 示例
jobs:
deploy:
steps:
- name: Switch to maintenance
run: ssh prod-server "php artisan down --secret=secret-token"
- name: Deploy code
uses: appleboy/ssh-action@master
with:
script: |
git pull
composer install --no-dev
php artisan migrate --force
- name: Warm cache
run: ssh prod-server "php artisan config:cache && php artisan route:cache"
- name: Restart workers
run: ssh prod-server "php artisan horizon:terminate"
- name: Bring application up
run: ssh prod-server "php artisan up"
6. 📊 监控体系搭建
Prometheus + Grafana 必备指标:
// 暴露自定义指标
use Prometheus\CollectorRegistry;
$registry = CollectorRegistry::getDefault();
$requestDuration = $registry->getOrRegisterHistogram(
'laravel_http_duration_seconds',
'HTTP request duration',
['method', 'route']
);
$requestDuration->observe($duration, [$method, $route]);
三、云原生时代进阶路线
🐳 Laravel on Kubernetes 架构
graph LR
A[用户] --> B[Ingress-Nginx]
B --> C[Laravel Pod]
C --> D[Redis Sentinel]
C --> E[MySQL Group Replication]
C -->|异步任务| F[Horizon Worker Pod]
D --> G[Prometheus Operator]
🔍 性能调优三阶法
- 代码层:Telescope 分析 N+1 查询
- 运行时:Blackfire 生成火焰图
- 基础设施:
kubectl top pod
定位资源瓶颈
☄️ 灾备设计
# 数据库快速回档
mysqldump -uuser -p dbname | gzip > db_$(date +%F).sql.gz # 每日备份
mysql -e "STOP SLAVE; START SLAVE UNTIL SQL_AFTER_GTIDS='xxxx'" # 精准回档
四、运维安全红线(违反=事故)
- 永不在
.env
中提交密码 → 使用 Vault/Secrets Manager - 永不以
root
运行 PHP-FPM → 专用 www-data 用户 - 永不直接操作生产数据库 → 必须走迁移脚本
- 永不关闭
APP_DEBUG=true
上线
五、工具箱精选
类别 | 工具 | 解决痛点 |
---|---|---|
本地调试 | Laravel Telescope + Xdebug | 追踪请求链路 |
性能剖析 | Blackfire.io + Swoole | 定位 CPU 热点 |
容器化 | Laravel Sail + K8s Operator | 快速构建生产环境 |
日志管理 | Logflare + Elastic APM | 分布式追踪 |
安全扫描 | EnvSecurityScanner + SonarQube | 检测配置泄露 |
你想手动登录服务器修复时,问自己三次 —— “这个操作能否自动化?”
# 将此加入你的部署前检查清单
php artisan optimize:clear # Laravel 9+
php artisan config:cache
chmod -R ug+rwx storage # ACL 权限
kubectl rollout restart deployment/laravel-app # K8s 热更新