Laravel 11 升级时 vendor:publish --force 会无条件覆盖所有带 config 标签的包配置文件,导致手动修改(字段增删、注释、环境适配)被静默删除;须先 git add config/、检查 git status --short config/、备份 config 目录,再选用精准发布或强制覆盖+git checkout 还原策略。

升级 Laravel 11 时,vendor:publish 默认跳过已存在的配置文件,但若你手动执行 php artisan vendor:publish --force 强制更新,【会无条件覆盖 config/ 目录下所有匹配的包配置文件】,你对 config/my-package.php 做过的任何字段增删、环境适配、注释说明都将被 silently 删除,且不会提示、不进 Git 暂存区、不生成 diff。
确认哪些配置文件会被 publish 影响
运行以下命令查看当前可发布的资源列表:
php artisan vendor:publish --list
重点关注输出中带 config 标签的行,例如:Provider: Spatie\Permission\PermissionServiceProvider → Tag: config。这些才是真正会被 --force 覆盖的目标。
注意:不是所有第三方包都走 config 标签发布——有些用自定义 tag(如 laravel-scout 用 scout),有些甚至不提供 publish 机制,直接 require() 加载。只盯住 Tag: config 行即可。
升级前必须做的三步保护
第一步:用 Git 暂存所有 config 文件变更
git add config/
第二步:检查是否有未提交的手动修改
git status --short config/ → 若输出非空(如 M config/sanctum.php),说明该文件已被你改过,必须先 commit 或 stash。
第三步:导出当前配置快照(可选但强烈建议)
执行 cp -r config/ config-backup-$(date +%Y%m%d)(Linux/macOS)或在 Windows 下手动复制整个 config 文件夹并重命名为 config-backup-20260806。这比 Git 更可靠——Git 不跟踪空目录,也不保存 .env 中未体现的逻辑分支判断。
安全更新配置文件的两种方法
方法一:精准发布 + 手动合并(推荐用于生产环境)
不加 --force,只发布特定包:
Laravel Cloud(cloud.laravel.com)。此技能用于处理所有 Laravel Cloud 请求,包括搜索和读取数据。只要任务涉及 Laravel Cloud,即使用此技能。
php artisan vendor:publish --provider="Spatie\Permission\PermissionServiceProvider" --tag="config"
此时命令会跳过已存在的 config/permission.php,仅当该文件不存在时才复制。你只需打开新发布的文件,逐项对比新增键(如 'teams' => false)、默认值变更(如 'cache_expires_after' => 3600 改为 7200),再手工补到你当前的配置里。
方法二:强制覆盖 + 立即还原关键字段(适用于本地快速同步)
执行 php artisan vendor:publish --tag="config" --force 后,立刻运行:
git checkout HEAD -- config/*.php
这一步会把所有 config 文件瞬间回退到上次 commit 状态,只保留你刚手动添加的新键值——因为 Git 不会记录 --force 写入的内容,它只认你 commit 过的版本。你只需再打开 diff 工具(如 VS Code 的 Source Control 面板),把包里新增的 default 值复制过来即可。
【切勿在未 commit 的状态下执行 --force】,否则 git checkout 无法恢复,只能从备份文件夹里手动拷贝。
升级后验证配置是否生效
清空配置缓存:
php artisan config:clear
然后立即检查某项关键配置是否读取正确:
php artisan tinker → 输入 config('sanctum.expiration') → 回车,确认返回值是你期望的数字,而非 null 或旧默认值。
如果返回 null,说明 config/sanctum.php 未被加载,大概率是文件权限问题(Windows 下常见)或命名错误(如写成 sanctum.php.bak)。此时不要重跑 publish,先检查文件名和目录层级。

















