Octane 是 Laravel 的常驻内存服务器,不能直接替换 PHP-FPM;它通过复用应用实例提升性能,需停用 FPM 并改用其内置 HTTP 服务或反向代理,依赖 PHP 8.0+、Swoole 4.8+ 或 RoadRunner 2022.3+。

Octane 是什么,它真能直接替换 PHP-FPM?
不能。Octane 不是 PHP-FPM 的“升级版”,而是完全不同的请求生命周期模型:它让 Laravel 应用常驻内存,复用已加载的类、配置和容器实例,跳过每次请求重复的 autoload、config:cache、服务注册等开销。你得主动停掉 Nginx/Apache 的 PHP-FPM 代理配置,改用 Octane 自带的 HTTP 服务器(或通过反向代理对接)。
常见错误现象:Class 'Laravel\Octane\OctaneServiceProvider' not found——没执行 composer require laravel/octane;或者运行 php artisan octane:start 后浏览器打不开,大概率是端口被占(默认 127.0.0.1:8000),或防火墙拦截。
- 必须用 PHP 8.0+,Swoole 扩展需 4.8+,RoadRunner 需 2022.3+(RR v2.15+ 更稳)
- 不兼容所有依赖:比如某些用
sleep()或pcntl_fork()的包,在协程环境下会阻塞整个 worker -
$_SERVER、$_GET等超全局变量在 Octane 中是只读快照,修改无效;要用request()->query()等 Laravel 封装方式
选 Swoole 还是 RoadRunner?看运维习惯和扩展需求
Swoole 更贴近 PHP 开发者直觉:纯 PHP 编写、扩展机制成熟、协程调试工具(如 co::stats())丰富;但对系统依赖多(需编译安装扩展)、Windows 支持弱、部分旧扩展(如 xdebug)与协程不兼容。
RoadRunner 是 Go 写的二进制 server,PHP 进程通过 RPC 通信,天然隔离、更稳定,且支持 HTTP/2、gRPC、队列 worker 多路复用;但它要求你额外维护一个 rr.yaml 配置文件,PHP 侧看不到底层连接状态。
立即学习“PHP免费学习笔记(深入)”;
- 开发阶段优先试 Swoole:
php artisan octane:start --server=swoole - 生产环境若已有 Go 运维能力、或需要混跑 HTTP + Queue + GRPC,选 RoadRunner:
php artisan octane:start --server=roadrunner,再确保rr命令在$PATH中 - 两者都不支持
opcache.enable_cli=1下的 CLI 模式热重载,改代码后必须手动php artisan octane:reload
哪些 Laravel 功能在 Octane 下会出问题?
核心原则:任何依赖“请求-响应一次性生命周期”的逻辑,在长连接、复用进程下容易残留状态。最典型的是静态属性、单例绑定、未重置的全局变量。
常见错误现象:Auth::user() 返回上一个用户的登录信息;缓存驱动(如 file)因路径未按请求隔离导致冲突;日志写入错乱。
- 避免在服务提供者中绑定单例到容器:
$this->app->singleton('xxx', ...)→ 改用scoped或每次请求 new 实例 - 不要在中间件或控制器里直接操作
$_SESSION;Session 必须走 Laravel 的StartSession中间件,且驱动建议用redis或database,别用file - 数据库连接默认不会自动释放,大查询后记得调用
DB::purge(),或设'options' => [PDO::ATTR_PERSISTENT => false]在config/database.php中
启动后怎么验证是否真在跑 Octane?
别只看 ps aux | grep octane,那只能说明进程起来了。关键看请求是否绕过了 FPM,以及是否复用了应用实例。
实操建议:在路由闭包里加一行 Log::info('Request ID: ' . uniqid());,然后连续刷新页面——如果日志里出现相同 uniqid()(说明应用没重建),或日志时间戳间隔远小于 100ms(FPM 通常 200ms+),基本就是跑起来了。
- 检查响应头:
X-Powered-By会变成Octane(Swoole)或RoadRunner(RR),不是PHP/8.x - 用
php artisan octane:status查看当前 worker 数、内存占用、请求计数 - 注意:Octane 默认不加载
.env的全部变量,敏感配置(如APP_KEY)必须提前php artisan config:cache,否则启动失败报Undefined index: APP_KEY
最难调的永远不是启动那一行命令,而是那些你以为“跟以前一样”的静态变量、单例、全局状态——它们在 Octane 里不会自动清空,得你亲手重置或换设计。











