frankenphp默认server模式不支持热更新,仅worker模式(需显式启用--worker或frankenphp_worker=1)才具备常驻进程与文件监听能力;其热更新依赖正确挂载路径、inotify事件通路及opcache配置(如opcache.validate_timestamps=1)四者协同。

FrankenPHP容器里代码不热更新?先确认是否用了Worker模式
FrankenPHP默认启动是Server模式(类似传统PHP-FPM + Nginx),它不会自动监听文件变化;只有启用--worker或FRANKENPHP_WORKER=1时,才进入常驻进程+热重载逻辑。如果你没显式开启Worker模式,改了宿主机代码,容器内根本不会触发重新加载——不是挂载失效,是根本没设计这功能。
- 检查启动命令是否含
--worker,例如:frankenphp serve --worker --config ./frankenphp.yaml - 若用Docker,确认环境变量设了
FRANKENPHP_WORKER=1,而非只设FRANKENPHP_SERVER=1 - Worker模式下,FrankenPHP会监听
public/和config/等目录变更,但不会扫描整个项目根目录;确保你改的文件在它监控路径内
挂载路径对不上,FrankenPHP根本看不到新代码
FrankenPHP运行时读取的是容器内路径(如/app),如果docker-compose.yml里的volumes映射写成./src:/var/www/html,但FrankenPHP配置里指定的是documentRoot: /app/public,那宿主机改./src完全无效——两边压根不在一个目录树下。
- 进容器执行
ls -l /app/public,看列出的文件是否和宿主机目标目录一致 - 用
docker inspect确认挂载是否生效:docker inspect <container_id> | jq '.[0].Mounts'</container_id>,重点看Source和Destination字段 - Linux用户若用rootless Docker,挂载可能被拒绝,加
:z后缀试试:./src:/app:z
文件权限或SELinux拦住了文件变更通知
FrankenPHP Worker依赖inotify监听文件系统事件。如果挂载目录权限太紧(比如宿主机上chmod 400),或者启用了SELinux(常见于CentOS/RHEL),inotify可能收不到IN_MODIFY事件,导致“文件明明改了,但FrankenPHP无反应”。
- 宿主机上运行
inotifywait -m -e modify,attrib,move ./src,再改一个PHP文件,看是否有输出;没输出就说明底层事件没通 - 临时禁用SELinux测试:
sudo setenforce 0,再试热更新;若恢复了,需给挂载目录加context="system_u:object_r:container_file_t:s0" - macOS用户注意:Docker Desktop默认用gRPC-FUSE挂载,对inotify支持有限,小文件变更有时延迟数秒甚至丢失,别依赖它做开发态实时反馈
FrankenPHP缓存了OPcache,改了代码但还在跑旧字节码
即使Worker模式启用、挂载正确、权限OK,OPcache仍可能让FrankenPHP继续执行旧的编译结果。它不像Swoole那样自动清opcache,需要手动干预或配置策略。
- 在FrankenPHP配置中显式关闭:
opcache.enable = 0(开发阶段推荐) - 或保留OPcache但强制检查更新:
opcache.validate_timestamps = 1且opcache.revalidate_freq = 0 - 检查
phpinfo()输出里的opcache.enabled和opcache.status,确认值符合预期
--worker,却以为它该自动刷新。php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











