Skip to main content
在讓使用者自訂畫面或郵件範本的套件中,除了公開 View 之外,還需要一套能在保留已公開檔案的情況下進行更新的約定。即使修正了套件端的 Blade 檔案,使用端應用程式也不一定會渲染該檔案。 本頁以套件開發的基礎為前提,將 View 的選擇、檔案的公開與快取分開來思考。官方文件參照 Laravel 13,框架的實作參照最新版本 v13.34.0。

註冊與公開是不同的處理

loadViewsFrom() 會將搜尋路徑註冊至命名空間。publishes() 會註冊複製來源與複製目的地,實際的複製則由 vendor:publish 執行。在下列範例中,即使不公開也能使用 courier::deliveries.show。
src/CourierServiceProvider.php
套件端的檔案放在 resources/views/deliveries/show.blade.php。View 名稱中的點會在搜尋時轉換為目錄分隔符號。
resources/views/deliveries/show.blade.php
View 的命名空間與 Composer 的套件名稱或 PHP 的命名空間無關。在此,loadViewsFrom() 第 2 個引數所指定的 courier,就是 View 參照與覆寫目錄的約定。

以檔案為單位尋找覆寫位置

ServiceProvider::loadViewsFrom() 會在 view 被解析時,依序確認設定中的 view.paths。若各路徑下存在 vendor/courier 目錄,就將該目錄加入命名空間,最後再加入套件端的路徑。 FileViewFinder 會依序搜尋該命名空間的路徑,並回傳最先找到的檔案。在使用標準 resources/views 的配置下,順序如下。 這並不是切換整個目錄。即使使用者只覆寫了 deliveries/show.blade.php,其他未覆寫的 View 仍會從套件端載入。
在有多個 view.paths 的配置中,覆寫位置也可能有多個。resource_path('views/vendor/courier') 只是此範例的公開目的地,並不是將搜尋對象固定在該處的處理。請讓命名空間保持套件專屬,並避免由多個服務提供者對同一名稱加入路徑的設計。

只自訂需要的 View

使用者可以透過下列指令複製範本。請指定服務提供者與標籤,避免連同其他資源一起公開。
此註冊會公開整個 View 目錄。若不需要覆寫全部內容,也可以在確認內容後只保留要自訂的檔案,或只將需要的檔案手動複製到相同的相對路徑。這是因為即使是未經編輯的副本,只要存在就會被視為覆寫。
已公開的範本不會隨套件更新自動同步。在舊副本優先的狀態下只修正套件端,該 View 的變更不會反映出來。顯示問題的修正或表單變更等,也需要與覆寫檔案進行比對。

重新公開不會合併差異

VendorPublishCommand 通常會在同名的公開目的地檔案存在時略過複製。--force 會覆寫既有檔案。此外,--existing 也是「覆寫已公開檔案」的選項,而不是保留使用者編輯內容的模式。 任何一種方式都不是比對舊版、新版與使用者編輯內容後的合併,也不會自動從公開目的地移除已從套件刪除的 View。請不要讓更新步驟只是「重新公開同一個標籤」。

將 View 也當作公開 API 來維護

不只是 View 名稱,接收的資料與參照的元件也會影響使用者的自訂內容。例如,若新版將 trackingCode 改為其他變數名稱,保留舊範本的使用者將無法從新程式碼取得所需的值。 發行前,請確認下列約定。
  • 不要隨意變更命名空間以及 deliveries.show 等 View 名稱。
  • 記錄傳入的變數、型別,以及必填與選填的區別。
  • 將 @include 與 @extends 的參照對象、Blade 元件的 props 也納入變更項目。
  • 在發行說明中記載修正過的 View,以及應套用至已公開舊版的變更。
為使用者準備一套比對舊版與新版套件 View、並將必要變更手動合併至已自訂檔案的步驟。對於不再需要覆寫的檔案,先透過備份或版本控制保全變更後再移除,即可回到套件端的 View。

Blade 快取不會更新覆寫檔案

view:cache 會將 Blade 範本預先編譯為 PHP。ViewCacheCommand 會先執行 view:clear,再收集一般的 View 路徑與註冊至命名空間的路徑,找出編譯對象。
此處理不會改寫已公開的 Blade 檔案,也不會改變 View 的搜尋優先順序。若存在舊的覆寫檔案,即使重建快取,仍會繼續選用該檔案。部署時,請先完成程式碼與覆寫檔案的更新再進行編譯。 開發中若想刪除已編譯的檔案並重新渲染,請使用下列指令。
若一般的時間戳記檢查已啟用,Blade 編譯器會比較原始檔案與已編譯檔案的更新時間。不過,也有停用時間戳記檢查的配置,因此請不要將部署時的重建完全交給自動判斷。

與搜尋結果的快取區分開來

FileViewFinder::find() 會將找到的路徑儲存在該 Finder 實例的 $views 陣列中。此外,覆寫目錄是否存在的確認是在 loadViewsFrom() 的回呼中進行。即使在啟動後新增目錄,也不會自動加入已註冊的搜尋路徑。 view:clear 並不是一次清除其他執行中處理程序所持有之 Finder 狀態的指令。在 Octane 等長時間執行的處理程序中,請依照一般的部署步驟重新載入。Finder 的 flush() 會清除搜尋結果,但不會進一步註冊新的覆寫目錄。

發行前應確認的事項

除了套件的測試之外,也請在使用端應用程式中確認下列組合。只渲染最新範本的測試,無法驗證對已公開舊版之使用者的相容性。
  • 在未公開的狀態下,會渲染套件的 View。
  • 只覆寫 1 個檔案時,只有該檔案優先,其他檔案會退回使用套件的 View。
  • 即使保留舊版已公開的範本,也能以新版傳入的資料進行渲染。
  • 一般的重新公開會保留自訂內容,未公開檔案的新增也符合預期。
  • 變更覆寫檔案後 view:cache 能成功執行,且在新的啟動中顯示變更後的內容。

相關頁面

View

確認 View 的建立、資料傳遞與預先編譯的基礎。

Blade 範本

確認版面配置、include 與元件的使用方式。

版本相容性管理

將範本的約定變更連結至發行方針。

Octane

確認長時間執行之應用程式的生命週期與重新載入。

參考的一手資料

最後修改於 2026年10月4日